Πώς να διασφαλίσετε καταχωρίσεις με μη επικαλυπτόμενα χρονικά όρια;

ψήφοι
50

Πρέπει να διασφαλίσω ότι η βάση δεδομένων μου περιέχει μόνο καταχωρήσεις όπου δύο ή περισσότερες στήλες είναι μοναδικές. Αυτό μπορεί εύκολα να επιτευχθεί με ένα UNIQUE περιορισμός σε αυτές τις στήλες.

Στην περίπτωσή μου, πρέπει να απαγορεύσω την επανάληψη μόνο για αλληλεπικαλυπτόμενα χρονικά διαστήματα. Ο πίνακας έχει valid_from και valid_to στήλες. Σε ορισμένες περιπτώσεις μπορεί πρώτα να χρειαστεί να λήξει η ενεργή καταχώριση με τη ρύθμιση valid_to = now και, στη συνέχεια, εισάγοντας μια νέα καταχώρηση προσαρμοσμένη σε valid_from = now και valid_to = infinity .

Φαίνεται ότι μπορώ να λήξω την προηγούμενη καταχώριση χωρίς προβλήματα στη χρήση UPDATE , αλλά η εισαγωγή της νέας καταχώρησης φαίνεται να είναι ενοχλητική, καθώς οι βασικές στήλες μου είναι αυτήν τη στιγμή UNIQUE και επομένως δεν μπορεί να προστεθεί ξανά.

Σκέφτηκα να προσθέσω valid_from και valid_to ως μέρος του UNIQUE περιορισμός, αλλά αυτό θα καθιστούσε τον περιορισμό πιο χαλαρό και θα επέτρεπε την ύπαρξη διπλών και αλληλεπικαλυπτόμενων χρονικών ορίων.

Πώς μπορώ να κάνω έναν περιορισμό για να διασφαλίσω ότι δεν υπάρχουν διπλότυπα με επικάλυψη valid_from και valid_totsrange ;

Φαίνεται να ψάχνω EXCLUDE USING GIST , αλλά δεν φαίνεται να υποστηρίζει πολλές στήλες; Αυτό δεν φαίνεται να λειτουργεί για μένα:

ALTER TABLE registration 
DROP Constraint IF EXISTS registration_{string.Join('_', listOfAttributes)}_key, 
ADD Constraint registration_{string.Join('_', listOfAttributes)}_key EXCLUDE USING GIST({string.Join(',', listOfAttributes)} WITH =, valid WITH &&);
Δημοσιεύθηκε 10/05/2020 στις 19:31
πηγή χρήστη
Σε άλλες γλώσσες...                            


1 απαντήσεις

ψήφοι
0

Ήσουν στο σωστό δρόμο. Ωστόσο, η σύνταξη για τους περιορισμούς αποκλεισμού είναι ελαφρώς διαφορετική:

CREATE TABLE registration  (
  tbl_id  integer PRIMARY KEY GENERATED BY DEFAULT AS IDENTITY
, col_a   integer NOT NULL
, col_b   integer NOT NULL
, valid_from timestamptz
, valid_to   timestamptz
, CONSTRAINT no_overlap
    EXCLUDE USING gist (col_a with =, col_b with =, tstzrange(valid_from, valid_to) WITH &&)
);

Ίσως χρειαστεί να εγκαταστήσετε την πρόσθετη μονάδα btree_gist πρώτα, ανάλογα με τον μη γνωστό ορισμό του πίνακα σας.

Κάθε στήλη πρέπει να αναφέρεται στον αντίστοιχο χειριστή της.

Και χρειάζεστε έναν τύπο εύρους . Υποθέτοντας timestamp with time zone Για valid_from και valid_to , η έκφραση tstzrange(valid_from, valid_to) θα το έκανε.

Σχετίζεται με:


Ίσως , ένας ανώτερος σχεδιασμός να είναι μια σχέση μεταξύ σας registration πίνακες και 1-Ν καταχωρήσεις σε μια νέα registration_range τραπέζι. Και κάποια λογική για τον προσδιορισμό της τρέχουσας έγκυρης καταχώρισης (για οποιαδήποτε δεδομένη χρονική στιγμή). Εξαρτάται από περισσότερες άγνωστες πληροφορίες.

Απαντήθηκε 13/05/2020 στις 18:31
πηγή χρήστη

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more