Ich versuche, die Geschäftslogik einer Intranet-C # -Webanwendung in der Datenbank zu duplizieren, damit andere Datenbanken darauf zugreifen und nach denselben Regeln arbeiten können. Diese "Regel" scheint ohne Hacks schwierig zu implementieren zu sein.
CREATE TABLE CASE_STAGE
(
ID NUMBER(9) PRIMARY KEY NOT NULL,
STAGE_ID NUMBER(9) NOT NULL,
CASE_PHASE_ID NUMBER(9) NOT NULL,
DATE_CREATED TIMESTAMP(6) DEFAULT CURRENT_TIMESTAMP NOT NULL,
END_REASON_ID NUMBER(9),
PREVIOUS_CASE_STAGE_ID NUMBER(9),
"CURRENT" NUMBER(1) NOT NULL,
DATE_CLOSED TIMESTAMP(6) DEFAULT NULL
);
und
CREATE TABLE CASE_RECOMMENDATION
(
CASE_ID NUMBER(9) NOT NULL,
RECOMMENDATION_ID NUMBER(9) NOT NULL,
"ORDER" NUMBER(9) NOT NULL,
DATE_CREATED TIMESTAMP(6) DEFAULT CURRENT_TIMESTAMP NOT NULL,
CASE_STAGE_ID NUMBER(9) NOT NULL
);
ALTER TABLE CASE_RECOMMENDATION ADD (
CONSTRAINT SYS_C00000
PRIMARY KEY
(CASE_ID, RECOMMENDATION_ID));
Die Geschäftslogik kann wie folgt zusammengefasst werden
When Inserting into CASE_STAGE
If CASE_STAGE.STAGE_ID = 1646
THEN
CASE_STAGE.PREVIOUS_STAGE_ID must be found in CASE_RECOMMENDATION.CASE_STAGE_ID
Kann diese Logik in einer Check-Einschränkung enthalten sein oder ist ein hässlicher Trigger der einzige Weg?
Bearbeiten:
- Für alle Werte von CASE_STAGE.STAGE_ID muss der Wert für PREVIOUS_STAGE_ID in CASE_STAGE.ID gefunden werden
- Die Anwendung erlaubt keine Löschungen aus CASE_RECOMMENDATION, wenn sie nicht mehr CURRENT ist (dh wenn der Wert von CASE_STAGE.CURRENT 0 ist, ist diese Stufe geschlossen und kann nicht mehr geändert werden, wenn = 1, ist dies die Stufe oder Zeile, die aktiv ist und kann jetzt geändert werden.)
Bearbeiten: Die Verwendung all der hervorragenden Ideen und Kommentare hier ist eine funktionierende Lösung für dieses Problem
CREATE MATERIALIZED VIEW LOG ON CASE_STAGE
TABLESPACE USERS
STORAGE (
BUFFER_POOL DEFAULT
)
NOCACHE
LOGGING
NOPARALLEL
WITH ROWID;
CREATE MATERIALIZED VIEW LOG ON CASE_RECOMMENDATION
TABLESPACE USERS
STORAGE (
BUFFER_POOL DEFAULT
)
NOCACHE
LOGGING
NOPARALLEL
WITH ROWID;
CREATE MATERIALIZED VIEW CASE_RECOMMENDATION_MV REFRESH FAST ON COMMIT AS
SELECT
cr.ROWID cr_rowid, --necessary for fast refresh
cs.ROWID cs_rowid, --necessary for fast refresh
cr.case_id,
cs.stage_id,
cr.recommendation_id
cr.case_stage_id,
cs.previous_case_stage_id
FROM CASE_RECOMMENDATION cr,
case_stage cs
WHERE cs.previous_case_stage_id = cr.case_stage_id (+)
AND CS.PREVIOUS_CASE_STAGE_ID IS NOT NULL
AND EXTRACT (YEAR FROM CS.DATE_CREATED) > 2010 --covers non conforming legacy data
AND CR.RECOMMENDATION_ID IS NULL
AND cs.stage_id =1646;
--this last line excludes everything but problem cases due to the outer join
ALTER TABLE CASE_RECOMMENDATION_MV ADD CONSTRAINT CASE_RECOMMENDATION_ck CHECK (
(previous_case_stage_id IS NOT NULL AND case_stage_id IS NOT NULL)
);
Beim Einfügen einer 1646-Stufe unter Verwendung vorhandener Pakete ohne Empfehlung war der Fehler
ORA-12008: error in materialized view refresh path
ORA-02290: check constraint (APPBASE.CASE_RECOMMENDATION_MV_C01) violated
ORA-06512: at line 49
Job erledigt! Nicht wofür eine materialisierte Ansicht gedacht war, sondern besser als ein Auslöser.
1646
? Ist es eine Option, das Design zu ändern (Tabelle in zwei Teile zu teilen)?
CASE_RECOMMENDATION.CASE_STAGE_ID
einzigartig?