Najlepsza praktyka przechowywania metadanych rekordów

10

Jaka jest najlepsza praktyka przechowywania metadanych poszczególnych rekordów w bazie danych?

Muszę przechowywać typowe dane meta, takie jak czas utworzenia i czas ostatniej aktualizacji dla wielu tabel w mojej bazie danych. Znalazłem kilka różnych rozwiązań:

  1. Przechowuj metadane bezpośrednio w tabelach.

    Plusy:

    • Metadane są bezpośrednio powiązane z rekordami
    • Do pobierania metadanych nie są wymagane połączenia

    Cons:

    • Wymaganych jest wiele zduplikowanych kolumn (chyba że zastosowano dziedziczenie)
    • Metadane i dane biznesowe nie są rozdzielane
  2. Utwórz ogólną tabelę metadanych i użyj miękkich kluczy obcych, aby połączyć dane z odpowiednimi tabelami i rekordami.

    Plusy:

    • Brak powielania kolumn
    • Metadane są oddzielone od danych biznesowych

    Cons:

    • Brak bezpośrednich powiązań między metadanymi i danymi (nie można użyć FK)
    • Połączenia wymagają dodatkowego warunku
  3. Utwórz osobne tabele metadanych dla każdej tabeli wymagającej metadanych.

    Plusy:

    • Metadane są bezpośrednio powiązane z rekordami
    • Metadane są oddzielone od danych biznesowych

    Cons:

    • Wymaganych jest wiele dodatkowych stolików
    • Wymaganych jest wiele zduplikowanych kolumn (chyba że zastosowano dziedziczenie)

Czy jest więcej opcji, zalet lub wad niż te, o których tu wspomniałem? A jaka jest najlepsza praktyka przechowywania tych metadanych?

Tiddo
źródło
O jakich metadanych mówimy? Może użycie kolumny hstorelub JSONmoże rozwiązać problem?
a_horse_w_no_name
@ a_horse_with_no_name - Teraz potrzebuję tylko czasu utworzenia, czasu aktualizacji i źródła tworzenia. Pola są ustalone, więc nie potrzebuję klucza-wartości, takich jak pamięć. Martwię się tylko o miejsce przechowywania danych.
Tiddo
1
Zatem nie widzę żadnego powodu, aby nie dodawać tych trzech kolumn do tabeli podstawowej.
a_horse_w_no_name

Odpowiedzi:

7

Kolumny, o których mówisz, zajmują 20 bajtów (jeśli są wyrównane bez wypełnienia):

czas utworzenia, czas aktualizacji i źródło tworzenia

znacznik czasu .. 8 bajtów
znacznik czasu .. 8 bajtów
liczba całkowita .. 4 bajty

Nagłówek krotki i wskaźnik pozycji dla osobnego wiersza w osobnej tabeli zajmowałby 23 + 1 + 4 = 28 bajtów plus 20 bajtów rzeczywistych danych plus 4 bajty wypełnienia na końcu. Wykonuje 52 bajty na wiersz . Przeczytaj więcej tutaj:

Jeśli chodzi o przechowywanie, nie masz nic do zyskania. Jeśli chodzi o wydajność, prawie nic nie tracisz, mając zaledwie 16–24 bajtów więcej na wiersz.

Kolumny również bezpośrednio należą do wiersza, więc warto je trzymać razem. Przyzwyczajam się, aby dodawać dokładnie takie kolumny (plus osobne źródło dla ostatniej aktualizacji) do wszystkich odpowiednich tabel.

Łatwiej jest również napisać, TRIGGER ON INSERT OR UPDATEaby były aktualne.

Krótko mówiąc: mocny głos na twoją opcję 1 .

Gdzie wybrałbym opcję 3 :
Jeśli metadane są często aktualizowane, a rdzeń nie jest. Wtedy warto byłoby zachować oddzielny stół 1: 1, aby tańsze aktualizacje i zmniejszyć wzdęcia na głównym stole - a nawet przejść do opcji 2.

Gdzie wybrałbym opcję 2 :
Jeśli zestaw kolumn metadanych jest wysoce powtarzalny. Możesz mieć kolumnę FK do zestawu metadanych w głównych tabelach. Nie oszczędza dużo dla trzech małych kolumn, jak w twoim przykładzie.

Erwin Brandstetter
źródło
Co z rozwiązaniem tego problemu z dziedziczeniem tabeli, czy istnieją znaczące wady w porównaniu do używania kolumn metadanych bezpośrednio w tabeli? Jeśli jednak dobrze rozumiem, dziedziczenie tabel Postgres nie jest zgodne ze standardem SQL, prawda?
devrys
1
@devrys: Dziedziczenie ma pewne ograniczenia w Postgres. Co ważniejsze: Nie widzę, jak dziedziczenie mogłoby rozwiązać zapisywanie dodatkowych kolumn w wierszu. byłaby to opcja, jeśli masz niektóre wiersze z i inne wiersze bez metadanych. Ale nie użyłbym tego do tego.
Erwin Brandstetter,