feat(deploy): TrueNAS Custom-App + Auto-Deploy, plus aufgelaufene Arbeit
Some checks failed
CI / Backend Tests (.NET) (push) Successful in 1m11s
CI / Frontend Tests (Node/Vite) (push) Failing after 4m59s
CI / Docker Build & Push (push) Has been skipped
CI / Deploy auf TrueNAS (Custom App) (push) Has been skipped

Deployment:
- custom-app.compose.yaml: self-contained Compose fuer TrueNAS "Custom App"
  (absolute Host-Bind-Pfade, postgres:18, pull_policy always, Port 8090)
- scripts/truenas-deploy.sh: Host-Skript create/redeploy via midclt (App
  bleibt unter Apps sichtbar) inkl. Image-Pull + Health-Check
- ci.yml Deploy-Job: laeuft auf ubuntu-latest-Runner, kopiert Deploy-Dateien
  per SSH auf den NAS-Host und triggert truenas-deploy.sh (statt runs-on goldeye)
- compose.yaml/.env.example: postgres:18 (Locale-Match zur Quell-DB), Port 8090
- .gitignore: .agents/, tools/rag/, deploy/truenas/.env (Secrets/Scratch)

Aufgelaufene Feature-Arbeit (verified/Freeze, Migrationen, Import-Triage):
- GerbilOverride/VerifiedGerbil-Endpoints + GerbilSnapshotService + Tests
- EF-Migrationen (ShowInChronicle, Stillborn, BirthOrder, ManualFlag, DSGVO)
- Frontend VerifizierteTierePage + verified-API + e2e-Spec
- diverse Import-/Triage-Skripte und -Tests

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-07-19 09:19:11 +02:00
parent 84365bba7f
commit 45b8533f18
93 changed files with 20477 additions and 432 deletions

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,32 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace GerbilManagerWebAPI.Migrations
{
/// <inheritdoc />
public partial class AddLitterShowInChronicle : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<bool>(
name: "ShowInChronicle",
table: "Litters",
type: "boolean",
nullable: false,
// Bestehende Würfe bleiben in der Wurfchronik sichtbar; nur explizit als
// „nicht in Chronik" importierte Würfe (z. B. Akanes extern entstandener Wurf)
// werden beim Ingest auf false gesetzt.
defaultValue: true);
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "ShowInChronicle",
table: "Litters");
}
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,47 @@
using System;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace GerbilManagerWebAPI.Migrations
{
/// <inheritdoc />
public partial class UpdateLegalPagesDsgvo : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.UpdateData(
table: "Blocks",
keyColumn: "Id",
keyValue: new Guid("51720002-0000-0000-0000-000000000070"),
column: "Data",
value: "{\"markdown\":\"## Angaben gemäß § 5 DDG (Digitale-Dienste-Gesetz)\\n\\nSeitenbetreiber:\\n[Vor- und Nachname]\\n[Straße und Hausnummer]\\n[PLZ und Ort]\\n\\n## Kontakt\\n\\nTelefon: [Telefonnummer]\\nE-Mail: [E-Mail-Adresse]\\n\\n## Verantwortlich für den Inhalt gemäß § 18 Abs. 2 MStV\\n\\n[Vor- und Nachname], Anschrift wie oben\\n\\n## Verbraucherstreitbeilegung\\n\\nWir sind nicht bereit oder verpflichtet, an Streitbeilegungsverfahren vor einer Verbraucherschlichtungsstelle teilzunehmen.\\n\\n---\\n\\n*Hinweis für den Seitenbetreiber: Bitte alle Platzhalter in eckigen Klammern durch deine echten Angaben ersetzen. Pflicht ist eine ladungsfähige Anschrift (kein Postfach). Wird die Zucht gewerblich betrieben oder besteht eine Erlaubnis nach § 11 TierSchG, ergänze hier die zuständige Behörde und das Aktenzeichen.*\"}");
migrationBuilder.UpdateData(
table: "Blocks",
keyColumn: "Id",
keyValue: new Guid("51720002-0000-0000-0000-000000000080"),
column: "Data",
value: "{\"markdown\":\"## Datenschutzerklärung\\n\\n## 1. Verantwortlicher\\n\\nVerantwortlich für die Datenverarbeitung auf dieser Webseite ist:\\n[Vor- und Nachname]\\n[Straße und Hausnummer]\\n[PLZ und Ort]\\nE-Mail: [E-Mail-Adresse]\\n\\n## 2. Hosting und Server-Logfiles\\n\\nDiese Webseite wird auf einem eigenen Server betrieben. Beim Aufruf der Seite verarbeitet der Server automatisch Informationen, die dein Browser übermittelt, in sogenannten Server-Logfiles: IP-Adresse, Datum und Uhrzeit des Zugriffs, die aufgerufene Seite bzw. Datei, die übertragene Datenmenge sowie Browser und Betriebssystem.\\nDiese Verarbeitung ist technisch erforderlich, um die Webseite auszuliefern und ihren sicheren und stabilen Betrieb zu gewährleisten. Rechtsgrundlage ist Art. 6 Abs. 1 lit. f DSGVO (berechtigtes Interesse am störungsfreien Betrieb und an der Sicherheit). Die Logfiles werden nach spätestens [z. B. 7] Tagen gelöscht und nicht mit anderen Daten zusammengeführt.\\n\\n## 3. Cookies, Tracking und externe Dienste\\n\\nDiese Webseite verwendet keine Cookies, kein Tracking und keine Analyse- oder Marketing-Dienste. Es werden keine externen Inhalte Dritter (z. B. Schriftarten, Karten, Videos, CDNs) nachgeladen.\\n\\n## 4. Kontaktaufnahme\\n\\nWenn du uns per E-Mail kontaktierst, verarbeiten wir deine Angaben (z. B. Name, E-Mail-Adresse, Inhalt der Nachricht) ausschließlich zur Bearbeitung deiner Anfrage. Rechtsgrundlage ist Art. 6 Abs. 1 lit. b DSGVO bzw. Art. 6 Abs. 1 lit. f DSGVO. Die Daten werden gelöscht, sobald sie nicht mehr benötigt werden und keine gesetzlichen Aufbewahrungspflichten entgegenstehen.\\n\\n## 5. Empfänger der Daten\\n\\nEine Weitergabe deiner Daten an Dritte findet nicht statt. Eine Datenübermittlung in Länder außerhalb der EU bzw. des EWR erfolgt nicht.\\n\\n## 6. Deine Rechte\\n\\nDu hast jederzeit das Recht auf:\\n- Auskunft über die zu deiner Person gespeicherten Daten (Art. 15 DSGVO)\\n- Berichtigung unrichtiger Daten (Art. 16 DSGVO)\\n- Löschung (Art. 17 DSGVO)\\n- Einschränkung der Verarbeitung (Art. 18 DSGVO)\\n- Datenübertragbarkeit (Art. 20 DSGVO)\\n- Widerspruch gegen die Verarbeitung (Art. 21 DSGVO)\\n\\nZur Ausübung genügt eine formlose Nachricht an die oben genannte E-Mail-Adresse.\\n\\n## 7. Beschwerderecht bei der Aufsichtsbehörde\\n\\nDu hast das Recht, dich bei einer Datenschutz-Aufsichtsbehörde zu beschweren (Art. 77 DSGVO). Zuständig ist die Aufsichtsbehörde deines Bundeslandes bzw. des Seitenbetreibers: [zuständige Landesdatenschutzbehörde eintragen].\\n\\n## 8. Keine automatisierte Entscheidungsfindung\\n\\nEine automatisierte Entscheidungsfindung einschließlich Profiling nach Art. 22 DSGVO findet nicht statt.\\n\\n---\\n\\n*Hinweis für den Seitenbetreiber: Platzhalter in eckigen Klammern ausfüllen. Aufbewahrungsdauer der Logfiles an deinen Server bzw. Reverse-Proxy anpassen. Sobald externe Dienste oder ein Kontaktformular eingebunden werden, diesen Text ergänzen. Stand: [Datum eintragen].*\"}");
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.UpdateData(
table: "Blocks",
keyColumn: "Id",
keyValue: new Guid("51720002-0000-0000-0000-000000000070"),
column: "Data",
value: "{\"markdown\":\"**Angaben gemäß § 5 TMG**\\n\\nSeitenbetreiber: [Name und vollständige Adresse eintragen]\\n\\nE-Mail: [E-Mail-Adresse eintragen]\\n\\n---\\n\\n*Diese Seite wird vom Seitenbetreiber noch vervollständigt.*\"}");
migrationBuilder.UpdateData(
table: "Blocks",
keyColumn: "Id",
keyValue: new Guid("51720002-0000-0000-0000-000000000080"),
column: "Data",
value: "{\"markdown\":\"**Datenschutzerklärung**\\n\\nDiese Webseite dient der Vorstellung unserer Rennmauszucht. Es werden keine personenbezogenen Daten gespeichert oder weitergegeben.\\n\\nBei datenschutzbezogenen Fragen: [E-Mail-Adresse eintragen]\\n\\n---\\n\\n*Diese Seite wird vom Seitenbetreiber noch vervollständigt.*\"}");
}
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,33 @@
using System;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace GerbilManagerWebAPI.Migrations
{
/// <inheritdoc />
public partial class UpdateImpressumHobbyMStV : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.UpdateData(
table: "Blocks",
keyColumn: "Id",
keyValue: new Guid("51720002-0000-0000-0000-000000000070"),
column: "Data",
value: "{\"markdown\":\"## Angaben gemäß § 18 Abs. 1 MStV\\n\\n[Vor- und Nachname]\\n[Straße und Hausnummer]\\n[PLZ und Ort]\\n\\n## Kontakt\\n\\nE-Mail: [E-Mail-Adresse]\\nTelefon: [Telefonnummer]\\n\\n---\\n\\nDiese Seite stellt eine private Hobbyzucht mongolischer Rennmäuse ohne Gewinnerzielungsabsicht vor.\\n\\n*Hinweis für den Seitenbetreiber: Name und ladungsfähige Anschrift (kein Postfach) sind Pflicht (§ 18 Abs. 1 MStV). Sollte die Zucht jemals gewerblich bzw. geschäftsmäßig betrieben werden, gelten zusätzlich § 5 DDG (vollständiges Anbieter-Impressum) und ggf. die Erlaubnispflicht nach § 11 TierSchG — dann zuständige Behörde und Aktenzeichen hier ergänzen. Kein Hinweis auf die EU-Streitbeilegungsplattform: diese wurde zum 20.07.2025 abgeschaltet (ein fortbestehender Link wäre irreführend).*\"}");
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.UpdateData(
table: "Blocks",
keyColumn: "Id",
keyValue: new Guid("51720002-0000-0000-0000-000000000070"),
column: "Data",
value: "{\"markdown\":\"## Angaben gemäß § 5 DDG (Digitale-Dienste-Gesetz)\\n\\nSeitenbetreiber:\\n[Vor- und Nachname]\\n[Straße und Hausnummer]\\n[PLZ und Ort]\\n\\n## Kontakt\\n\\nTelefon: [Telefonnummer]\\nE-Mail: [E-Mail-Adresse]\\n\\n## Verantwortlich für den Inhalt gemäß § 18 Abs. 2 MStV\\n\\n[Vor- und Nachname], Anschrift wie oben\\n\\n## Verbraucherstreitbeilegung\\n\\nWir sind nicht bereit oder verpflichtet, an Streitbeilegungsverfahren vor einer Verbraucherschlichtungsstelle teilzunehmen.\\n\\n---\\n\\n*Hinweis für den Seitenbetreiber: Bitte alle Platzhalter in eckigen Klammern durch deine echten Angaben ersetzen. Pflicht ist eine ladungsfähige Anschrift (kein Postfach). Wird die Zucht gewerblich betrieben oder besteht eine Erlaubnis nach § 11 TierSchG, ergänze hier die zuständige Behörde und das Aktenzeichen.*\"}");
}
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,82 @@
using System;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace GerbilManagerWebAPI.Migrations
{
/// <inheritdoc />
public partial class AddVerifiedGerbilAndManualFlag : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<bool>(
name: "IsManual",
table: "Litters",
type: "boolean",
nullable: false,
defaultValue: false);
migrationBuilder.AddColumn<bool>(
name: "IsManual",
table: "Gerbils",
type: "boolean",
nullable: false,
defaultValue: false);
migrationBuilder.AddColumn<bool>(
name: "IsManual",
table: "Contacts",
type: "boolean",
nullable: false,
defaultValue: false);
migrationBuilder.CreateTable(
name: "GerbilOverrides",
columns: table => new
{
Id = table.Column<Guid>(type: "uuid", nullable: false),
GerbilId = table.Column<Guid>(type: "uuid", nullable: false),
EntityName = table.Column<string>(type: "text", nullable: true),
IsVerified = table.Column<bool>(type: "boolean", nullable: false),
OverrideJson = table.Column<string>(type: "text", nullable: false),
SnapshotJson = table.Column<string>(type: "text", nullable: true),
LastImportSnapshotJson = table.Column<string>(type: "text", nullable: true),
LastImportDiffJson = table.Column<string>(type: "text", nullable: true),
Note = table.Column<string>(type: "text", nullable: true),
VerifiedAt = table.Column<DateTimeOffset>(type: "timestamp with time zone", nullable: true),
UpdatedAt = table.Column<DateTimeOffset>(type: "timestamp with time zone", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("PK_GerbilOverrides", x => x.Id);
});
migrationBuilder.CreateIndex(
name: "IX_GerbilOverrides_GerbilId",
table: "GerbilOverrides",
column: "GerbilId",
unique: true);
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "GerbilOverrides");
migrationBuilder.DropColumn(
name: "IsManual",
table: "Litters");
migrationBuilder.DropColumn(
name: "IsManual",
table: "Gerbils");
migrationBuilder.DropColumn(
name: "IsManual",
table: "Contacts");
}
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,28 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace GerbilManagerWebAPI.Migrations
{
/// <inheritdoc />
public partial class AddLitterStillborn : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<int>(
name: "Stillborn",
table: "Litters",
type: "integer",
nullable: true);
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "Stillborn",
table: "Litters");
}
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,28 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace GerbilManagerWebAPI.Migrations
{
/// <inheritdoc />
public partial class AddGerbilBirthOrder : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<int>(
name: "BirthOrder",
table: "Gerbils",
type: "integer",
nullable: true);
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "BirthOrder",
table: "Gerbils");
}
}
}

View File

@@ -147,7 +147,7 @@ namespace GerbilManagerWebAPI.Migrations
new
{
Id = new Guid("51720002-0000-0000-0000-000000000070"),
Data = "{\"markdown\":\"**Angaben gemäß § 5 TMG**\\n\\nSeitenbetreiber: [Name und vollständige Adresse eintragen]\\n\\nE-Mail: [E-Mail-Adresse eintragen]\\n\\n---\\n\\n*Diese Seite wird vom Seitenbetreiber noch vervollständigt.*\"}",
Data = "{\"markdown\":\"## Angaben gemäß § 18 Abs. 1 MStV\\n\\n[Vor- und Nachname]\\n[Straße und Hausnummer]\\n[PLZ und Ort]\\n\\n## Kontakt\\n\\nE-Mail: [E-Mail-Adresse]\\nTelefon: [Telefonnummer]\\n\\n---\\n\\nDiese Seite stellt eine private Hobbyzucht mongolischer Rennmäuse ohne Gewinnerzielungsabsicht vor.\\n\\n*Hinweis für den Seitenbetreiber: Name und ladungsfähige Anschrift (kein Postfach) sind Pflicht (§ 18 Abs. 1 MStV). Sollte die Zucht jemals gewerblich bzw. geschäftsmäßig betrieben werden, gelten zusätzlich § 5 DDG (vollständiges Anbieter-Impressum) und ggf. die Erlaubnispflicht nach § 11 TierSchG — dann zuständige Behörde und Aktenzeichen hier ergänzen. Kein Hinweis auf die EU-Streitbeilegungsplattform: diese wurde zum 20.07.2025 abgeschaltet (ein fortbestehender Link wäre irreführend).*\"}",
Order = 1,
PageId = new Guid("51720001-0000-0000-0000-000000000007"),
Type = "RichText"
@@ -163,7 +163,7 @@ namespace GerbilManagerWebAPI.Migrations
new
{
Id = new Guid("51720002-0000-0000-0000-000000000080"),
Data = "{\"markdown\":\"**Datenschutzerklärung**\\n\\nDiese Webseite dient der Vorstellung unserer Rennmauszucht. Es werden keine personenbezogenen Daten gespeichert oder weitergegeben.\\n\\nBei datenschutzbezogenen Fragen: [E-Mail-Adresse eintragen]\\n\\n---\\n\\n*Diese Seite wird vom Seitenbetreiber noch vervollständigt.*\"}",
Data = "{\"markdown\":\"## Datenschutzerklärung\\n\\n## 1. Verantwortlicher\\n\\nVerantwortlich für die Datenverarbeitung auf dieser Webseite ist:\\n[Vor- und Nachname]\\n[Straße und Hausnummer]\\n[PLZ und Ort]\\nE-Mail: [E-Mail-Adresse]\\n\\n## 2. Hosting und Server-Logfiles\\n\\nDiese Webseite wird auf einem eigenen Server betrieben. Beim Aufruf der Seite verarbeitet der Server automatisch Informationen, die dein Browser übermittelt, in sogenannten Server-Logfiles: IP-Adresse, Datum und Uhrzeit des Zugriffs, die aufgerufene Seite bzw. Datei, die übertragene Datenmenge sowie Browser und Betriebssystem.\\nDiese Verarbeitung ist technisch erforderlich, um die Webseite auszuliefern und ihren sicheren und stabilen Betrieb zu gewährleisten. Rechtsgrundlage ist Art. 6 Abs. 1 lit. f DSGVO (berechtigtes Interesse am störungsfreien Betrieb und an der Sicherheit). Die Logfiles werden nach spätestens [z. B. 7] Tagen gelöscht und nicht mit anderen Daten zusammengeführt.\\n\\n## 3. Cookies, Tracking und externe Dienste\\n\\nDiese Webseite verwendet keine Cookies, kein Tracking und keine Analyse- oder Marketing-Dienste. Es werden keine externen Inhalte Dritter (z. B. Schriftarten, Karten, Videos, CDNs) nachgeladen.\\n\\n## 4. Kontaktaufnahme\\n\\nWenn du uns per E-Mail kontaktierst, verarbeiten wir deine Angaben (z. B. Name, E-Mail-Adresse, Inhalt der Nachricht) ausschließlich zur Bearbeitung deiner Anfrage. Rechtsgrundlage ist Art. 6 Abs. 1 lit. b DSGVO bzw. Art. 6 Abs. 1 lit. f DSGVO. Die Daten werden gelöscht, sobald sie nicht mehr benötigt werden und keine gesetzlichen Aufbewahrungspflichten entgegenstehen.\\n\\n## 5. Empfänger der Daten\\n\\nEine Weitergabe deiner Daten an Dritte findet nicht statt. Eine Datenübermittlung in Länder außerhalb der EU bzw. des EWR erfolgt nicht.\\n\\n## 6. Deine Rechte\\n\\nDu hast jederzeit das Recht auf:\\n- Auskunft über die zu deiner Person gespeicherten Daten (Art. 15 DSGVO)\\n- Berichtigung unrichtiger Daten (Art. 16 DSGVO)\\n- Löschung (Art. 17 DSGVO)\\n- Einschränkung der Verarbeitung (Art. 18 DSGVO)\\n- Datenübertragbarkeit (Art. 20 DSGVO)\\n- Widerspruch gegen die Verarbeitung (Art. 21 DSGVO)\\n\\nZur Ausübung genügt eine formlose Nachricht an die oben genannte E-Mail-Adresse.\\n\\n## 7. Beschwerderecht bei der Aufsichtsbehörde\\n\\nDu hast das Recht, dich bei einer Datenschutz-Aufsichtsbehörde zu beschweren (Art. 77 DSGVO). Zuständig ist die Aufsichtsbehörde deines Bundeslandes bzw. des Seitenbetreibers: [zuständige Landesdatenschutzbehörde eintragen].\\n\\n## 8. Keine automatisierte Entscheidungsfindung\\n\\nEine automatisierte Entscheidungsfindung einschließlich Profiling nach Art. 22 DSGVO findet nicht statt.\\n\\n---\\n\\n*Hinweis für den Seitenbetreiber: Platzhalter in eckigen Klammern ausfüllen. Aufbewahrungsdauer der Logfiles an deinen Server bzw. Reverse-Proxy anpassen. Sobald externe Dienste oder ein Kontaktformular eingebunden werden, diesen Text ergänzen. Stand: [Datum eintragen].*\"}",
Order = 1,
PageId = new Guid("51720001-0000-0000-0000-000000000008"),
Type = "RichText"
@@ -756,6 +756,11 @@ namespace GerbilManagerWebAPI.Migrations
b.Property<bool>("IsBreeder")
.HasColumnType("boolean");
b.Property<bool>("IsManual")
.ValueGeneratedOnAdd()
.HasColumnType("boolean")
.HasDefaultValue(false);
b.Property<bool>("IsReceiver")
.HasColumnType("boolean");
@@ -998,6 +1003,9 @@ namespace GerbilManagerWebAPI.Migrations
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<int?>("BirthOrder")
.HasColumnType("integer");
b.Property<string>("CauseOfDeath")
.HasColumnType("text");
@@ -1042,6 +1050,11 @@ namespace GerbilManagerWebAPI.Migrations
b.Property<bool?>("IsDeaf")
.HasColumnType("boolean");
b.Property<bool>("IsManual")
.ValueGeneratedOnAdd()
.HasColumnType("boolean")
.HasDefaultValue(false);
b.Property<bool>("IsResident")
.ValueGeneratedOnAdd()
.HasColumnType("boolean")
@@ -1104,6 +1117,51 @@ namespace GerbilManagerWebAPI.Migrations
b.ToTable("Gerbils");
});
modelBuilder.Entity("GerbilManagerWebAPI.Models.GerbilOverride", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<string>("EntityName")
.HasColumnType("text");
b.Property<Guid>("GerbilId")
.HasColumnType("uuid");
b.Property<bool>("IsVerified")
.HasColumnType("boolean");
b.Property<string>("LastImportDiffJson")
.HasColumnType("text");
b.Property<string>("LastImportSnapshotJson")
.HasColumnType("text");
b.Property<string>("Note")
.HasColumnType("text");
b.Property<string>("OverrideJson")
.IsRequired()
.HasColumnType("text");
b.Property<string>("SnapshotJson")
.HasColumnType("text");
b.Property<DateTimeOffset>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.Property<DateTimeOffset?>("VerifiedAt")
.HasColumnType("timestamp with time zone");
b.HasKey("Id");
b.HasIndex("GerbilId")
.IsUnique();
b.ToTable("GerbilOverrides");
});
modelBuilder.Entity("GerbilManagerWebAPI.Models.GerbilPhoto", b =>
{
b.Property<Guid>("Id")
@@ -1187,6 +1245,11 @@ namespace GerbilManagerWebAPI.Migrations
b.Property<Guid?>("FatherId")
.HasColumnType("uuid");
b.Property<bool>("IsManual")
.ValueGeneratedOnAdd()
.HasColumnType("boolean")
.HasDefaultValue(false);
b.Property<string>("LitterLetter")
.HasColumnType("text");
@@ -1206,6 +1269,12 @@ namespace GerbilManagerWebAPI.Migrations
b.Property<string>("Provenance")
.HasColumnType("text");
b.Property<bool>("ShowInChronicle")
.HasColumnType("boolean");
b.Property<int?>("Stillborn")
.HasColumnType("integer");
b.Property<int?>("TotalBorn")
.HasColumnType("integer");