Files
Database/PRJ/PRJ_PAC.SRC
Peter Feij 9980977ee7 FSN#1254
svn path=/Database/trunk/; revision=9220
2006-05-12 14:34:30 +00:00

1128 lines
44 KiB
Plaintext

#ifdef PRJ
/* PRJ_PAC.SRC
*
* $Revision: 45 $
* $Modtime: 12-05-06 16:02 $
*/
#ifndef MS_SQL
CREATE OR REPLACE PACKAGE prj
AS
PROCEDURE prj_initiate_scenario (pscenariokey IN NUMBER, pverdiepingkey IN NUMBER);
PROCEDURE prj_copy_scenario (pscenariokey_from IN NUMBER, pscenariokey_to IN NUMBER);
PROCEDURE prj_reinitiate_scenario (pscenariokey IN NUMBER, pverdiepingkey IN NUMBER);
PROCEDURE prj_cancel_scenario (pscenariokey IN NUMBER, pverdiepingkey IN NUMBER);
PROCEDURE prj_commit_scenario (pscenariokey IN NUMBER);
PROCEDURE prj_move_werkplek (pwerkplekkey IN NUMBER, pruimtekey IN NUMBER);
PROCEDURE prj_move_perslidwerkplek (pperslidwerkplekkey IN NUMBER, pruimtekey IN NUMBER, pwerkplekkey IN NUMBER);
PROCEDURE prj_move_perslid (pperslidkey IN NUMBER, pruimtekey IN NUMBER, pwerkplekkey IN NUMBER);
FUNCTION forceuniqueness (element_type IN VARCHAR2, parent_key IN NUMBER, element_omschrijving IN VARCHAR2)
RETURN VARCHAR2;
END prj;
/
CREATE OR REPLACE PACKAGE BODY prj
AS
----------------------------------------------
-- UTILITY PROCEDURES AND FUNCTIONS
----------------------------------------------
PROCEDURE prj_log_clear (pscenariokey IN NUMBER)
IS
BEGIN
DELETE FROM prj_log
WHERE prj_scenario_key = pscenariokey;
END prj_log_clear;
PROCEDURE prj_log_add (
logmelding IN VARCHAR2,
code IN VARCHAR2,
pscenariokey IN NUMBER
)
IS
BEGIN
BEGIN
INSERT INTO prj_log
(prj_scenario_key, prj_log_omschrijving, prj_log_code
)
VALUES (pscenariokey, SUBSTR (logmelding, 1, 128), code
);
EXCEPTION
WHEN OTHERS
THEN
NULL;
END;
COMMIT;
END prj_log_add;
PROCEDURE checkscenario (pscenariokey IN NUMBER)
IS
dummy VARCHAR2 (1);
BEGIN
SELECT 'x'
INTO dummy
FROM prj_scenario s
WHERE s.prj_scenario_key = pscenariokey;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
raise_application_error
(-20001,
'prj package: invalid parameter pscenariokey'
);
RETURN;
END checkscenario;
FUNCTION forceuniqueness (
element_type IN VARCHAR2,
parent_key IN NUMBER,
element_omschrijving IN VARCHAR2
)
RETURN VARCHAR2
IS
omschrijving VARCHAR2 (30);
prefix VARCHAR2 (30);
BEGIN
IF element_type = 'ALG_RUIMTE'
THEN
/* Zoek op de geselecteerde verdieping of het huidige ruimtenummer al voor komt. */
BEGIN
SELECT g.alg_gebouw_code
|| '-'
|| TO_CHAR (v.alg_verdieping_code)
|| '-'
INTO prefix
FROM alg_gebouw g, alg_verdieping v, alg_ruimte r
WHERE g.alg_gebouw_key = v.alg_gebouw_key
AND v.alg_verdieping_key = r.alg_verdieping_key
AND r.alg_verdieping_key = parent_key
AND r.alg_ruimte_nr = element_omschrijving
AND r.alg_ruimte_verwijder IS NULL;
-- Gevonden, dus niet uniek. Probeer het met een sterretje ervoor, passen ze dat later maar zelf aan
omschrijving :=
forceuniqueness (element_type,
parent_key,
SUBSTR ('*' || element_omschrijving, 1, 10)
);
EXCEPTION
WHEN NO_DATA_FOUND
THEN
omschrijving := element_omschrijving;
END;
END IF;
-- Voor werkplekken, die een unieke numerieke ID hebben wordt gecheckt of de huidige waarde ok is,
-- en zoniet, dan wordt er doorgeteld tot de eersthogere wel unieke
IF element_type = 'PRS_WERKPLEK'
THEN
/* Zoek in de geselecteerde ruimte of het huidige werkpleknummer al voor komt. */
BEGIN
SELECT g.alg_gebouw_code
|| '-'
|| TO_CHAR (v.alg_verdieping_code)
|| '-'
|| TO_CHAR (r.alg_ruimte_nr)
INTO prefix
FROM alg_gebouw g,
alg_verdieping v,
alg_ruimte r,
prs_werkplek w
WHERE g.alg_gebouw_key = v.alg_gebouw_key
AND v.alg_verdieping_key = r.alg_verdieping_key
AND w.prs_alg_ruimte_key = r.alg_ruimte_key
AND w.prs_alg_ruimte_key = parent_key
AND w.prs_werkplek_volgnr = TO_NUMBER (element_omschrijving)
AND w.prs_werkplek_verwijder IS NULL;
-- Gevonden, dus niet uniek. Probeer het met een sterretje ervoor, passen ze dat later maar zelf aan
IF TO_NUMBER (element_omschrijving) = 999
THEN
-- Ik kan met 3 cijfers niet hoger, begin opnieuw onderaan (to prevent infinite recursion)
omschrijving :=
forceuniqueness (element_type, parent_key, '000');
ELSE
omschrijving :=
forceuniqueness (element_type,
parent_key,
TO_CHAR ( TO_NUMBER (element_omschrijving)
+ 1
)
);
END IF;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
omschrijving := element_omschrijving;
END;
END IF;
IF element_type = 'PRJ_WERKPLEK'
THEN
/* Zoek in de geselecteerde ruimte of het huidige werkpleknummer al voor komt. */
BEGIN
SELECT 'x'
INTO prefix
FROM prj_werkplek w
WHERE w.prj_ruimte_key = parent_key
AND w.prj_werkplek_volgnr = element_omschrijving
AND w.prj_werkplek_verwijder IS NULL;
-- Gevonden, dus niet uniek. Probeer het met een sterretje ervoor, passen ze dat later maar zelf aan
IF TO_NUMBER (element_omschrijving) = 999
THEN
-- Ik kan met 3 cijfers niet hoger, begin opnieuw onderaan (to prevent infinite recursion)
omschrijving :=
forceuniqueness (element_type, parent_key, '000');
ELSE
omschrijving :=
forceuniqueness (element_type,
parent_key,
TO_CHAR ( TO_NUMBER (element_omschrijving)
+ 1
)
);
END IF;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
omschrijving := element_omschrijving;
END;
END IF;
RETURN omschrijving;
END;
FUNCTION defaultwpomschrijving (pruimtekey IN NUMBER, pwerkpleknr IN NUMBER)
RETURN VARCHAR2
IS
omschrijving VARCHAR2 (30);
BEGIN
SELECT SUBSTR ( prj_ruimte_nr
|| '-'
|| LPAD (TO_CHAR (pwerkpleknr), 3, '0'),
1,
30
)
INTO omschrijving
FROM prj_ruimte
WHERE prj_ruimte_key = pruimtekey;
RETURN omschrijving;
END;
----------------------------------------------
-- SCENARIO MANAGEMENT PROCEDURES
----------------------------------------------
PROCEDURE prj_initiate_scenario (
pscenariokey IN NUMBER,
pverdiepingkey IN NUMBER
)
IS
dummy VARCHAR2 (1);
BEGIN
checkscenario (pscenariokey);
BEGIN
SELECT 'x'
INTO dummy
FROM alg_verdieping v
WHERE v.alg_verdieping_key = pverdiepingkey
AND v.alg_verdieping_verwijder IS NULL;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
raise_application_error
(-20001,
'prj_initiate_scenario: invalid parameter pverdiepingkey'
);
RETURN;
END;
BEGIN
SELECT 'x'
INTO dummy
FROM prj_ruimte rx
WHERE rx.alg_verdieping_key = pverdiepingkey
AND rx.prj_scenario_key = pscenariokey;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
NULL;
WHEN OTHERS
THEN
-- Bestaat al; niks doen en gewoon terugkeren
NULL;
RETURN;
END;
-- ** Parameters are proven valid
-- ?? Check of er al een kopie bestaat nodig ??
-- Kopieer de ruimtes
INSERT INTO prj_ruimte
(prj_ruimte_key, prj_scenario_key, alg_ruimte_key,
alg_verdieping_key, alg_srtruimte_key, prj_ruimte_nr,
prj_ruimte_omschrijving, prj_ruimte_bruto_vloeropp,
prj_ruimte_omtrek, prj_ruimte_inhoud)
SELECT NULL, pscenariokey, alg_ruimte_key, alg_verdieping_key,
alg_srtruimte_key, alg_ruimte_nr, alg_ruimte_omschrijving,
alg_ruimte_bruto_vloeropp, alg_ruimte_omtrek,
alg_ruimte_inhoud
FROM alg_ruimte r
WHERE r.alg_ruimte_verwijder IS NULL
AND alg_verdieping_key = pverdiepingkey;
-- Kopieer de werkplekken
INSERT INTO prj_werkplek
(prj_werkplek_key, prs_werkplek_key, prj_werkplek_volgnr,
prj_werkplek_omschrijving, prj_werkplek_vastopp,
prj_ruimte_key)
SELECT NULL, prs_werkplek_key, prs_werkplek_volgnr,
prs_werkplek_omschrijving, prs_werkplek_vastopp,
prj_ruimte_key
FROM prs_werkplek w, prj_ruimte rx
WHERE w.prs_alg_ruimte_key = rx.alg_ruimte_key
AND w.prs_werkplek_verwijder IS NULL
AND rx.prj_scenario_key = pscenariokey
AND rx.alg_verdieping_key = pverdiepingkey;
-- Kopieer de werkplekbezettingen
-- Persoonsbezetting: zoek de afdeling van de persoon erbij
INSERT INTO prj_perslidwerkplek
(prj_perslidwerkplek_key, prs_perslidwerkplek_key,
prs_perslid_key, prs_afdeling_key, prj_werkplek_key,
prj_perslidwerkplek_bezetting)
SELECT NULL, pw.prs_perslidwerkplek_key, pw.prs_perslid_key,
p.prs_afdeling_key, wx.prj_werkplek_key,
pw.prs_perslidwerkplek_bezetting
FROM prs_perslidwerkplek pw,
prj_werkplek wx,
prj_ruimte rx,
prs_perslid p
WHERE pw.prs_werkplek_key = wx.prs_werkplek_key
AND pw.prs_perslidwerkplek_verwijder IS NULL
AND rx.prj_scenario_key = pscenariokey
AND pw.prs_perslid_key IS NOT NULL
AND pw.prs_perslid_key = p.prs_perslid_key
AND wx.prj_ruimte_key = rx.prj_ruimte_key
AND rx.alg_verdieping_key = pverdiepingkey
UNION
SELECT NULL, pw.prs_perslidwerkplek_key, NULL, pw.prs_afdeling_key,
wx.prj_werkplek_key, pw.prs_perslidwerkplek_bezetting
FROM prs_perslidwerkplek pw, prj_werkplek wx, prj_ruimte rx
WHERE pw.prs_werkplek_key = wx.prs_werkplek_key
AND pw.prs_perslidwerkplek_verwijder IS NULL
AND rx.prj_scenario_key = pscenariokey
AND pw.prs_perslid_key IS NULL
AND wx.prj_ruimte_key = rx.prj_ruimte_key
AND rx.alg_verdieping_key = pverdiepingkey;
-- Kopieer de objecten
INSERT INTO prj_deel
(prj_deel_key, ins_deel_key, prj_ruimte_key,
prj_deel_omschrijving, ins_srtdeel_key)
SELECT NULL, ins_deel_key, rx.prj_ruimte_key, ins_deel_omschrijving,
d.ins_srtdeel_key
FROM ins_deel d, alg_v_aanwezigruimte r, prj_ruimte rx
WHERE d.ins_alg_ruimte_type = 'R'
AND d.ins_alg_ruimte_key = r.alg_ruimte_key
AND d.ins_deel_parent_key IS NULL
AND d.ins_deel_verwijder IS NULL
AND rx.prj_scenario_key = pscenariokey
AND rx.alg_ruimte_key = r.alg_ruimte_key
AND r.alg_verdieping_key = pverdiepingkey;
INSERT INTO prj_deel
(prj_deel_key, ins_deel_key, prj_ruimte_key,
prj_werkplek_key, prj_deel_omschrijving, ins_srtdeel_key)
SELECT NULL, ins_deel_key, rx.prj_ruimte_key, ins_alg_ruimte_key,
ins_deel_omschrijving, d.ins_srtdeel_key
FROM ins_deel d,
alg_v_aanwezigruimte r,
prs_v_aanwezigwerkplek w,
prj_ruimte rx
WHERE d.ins_alg_ruimte_type = 'W'
AND d.ins_alg_ruimte_key = w.prs_werkplek_key
AND w.prs_alg_ruimte_key = r.alg_ruimte_key
AND d.ins_deel_parent_key IS NULL
AND d.ins_deel_verwijder IS NULL
AND rx.prj_scenario_key = pscenariokey
AND rx.alg_ruimte_key = r.alg_ruimte_key
AND r.alg_verdieping_key = pverdiepingkey;
COMMIT;
END prj_initiate_scenario;
PROCEDURE prj_copy_scenario (
pscenariokey_from IN NUMBER,
pscenariokey_to IN NUMBER
)
IS
dummy VARCHAR2 (1);
BEGIN
checkscenario (pscenariokey_from);
checkscenario (pscenariokey_to);
BEGIN
SELECT 'x'
INTO dummy
FROM prj_ruimte rx
WHERE rx.prj_scenario_key = pscenariokey_to;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
NULL;
WHEN OTHERS
THEN
-- Bestaat al; niks doen en gewoon terugkeren
NULL;
RETURN;
END;
raise_application_error
(-20002,
'prj package: copy not yet supported'
);
RETURN;
-- ** Parameters are proven valid
-- Kopieer de ruimtes
INSERT INTO prj_ruimte
(prj_ruimte_key, prj_scenario_key, alg_ruimte_key,
alg_verdieping_key, alg_srtruimte_key, prj_ruimte_nr,
prj_ruimte_omschrijving, prj_ruimte_bruto_vloeropp,
prj_ruimte_omtrek, prj_ruimte_inhoud)
SELECT NULL, pscenariokey_to, alg_ruimte_key, alg_verdieping_key,
alg_srtruimte_key, prj_ruimte_nr, prj_ruimte_omschrijving,
prj_ruimte_bruto_vloeropp, prj_ruimte_omtrek,
prj_ruimte_inhoud
FROM prj_ruimte rx
WHERE prj_scenario_key = pscenariokey_from;
/* vergt nog wat uitwerking: de parent key van de zojuist aangemaakte ruimte etc gebruiken
-- Kopieer de werkplekken
INSERT INTO prj_werkplek
(prj_werkplek_key, prs_werkplek_key, prj_werkplek_volgnr,
prj_werkplek_omschrijving, prj_werkplek_vastopp,
prj_ruimte_key)
SELECT NULL, wx.prs_werkplek_key, wx.prj_werkplek_volgnr,
wx.prj_werkplek_omschrijving, wx.prj_werkplek_vastopp,
wx.prj_ruimte_key
FROM prj_werkplek wx, prj_ruimte rx, prj_ruimte rxx
WHERE wx.prj_ruimte_key = rx.prj_ruimte_key
AND rx.prj_ruimte_nr=wxx.prj_ruimte_nr
AND rx.alg_verdieping_key=rxx.alg_verdieping_key
AND rx.prj_scenario_key = pscenariokey_from;
-- Kopieer de werkplekbezettingen
INSERT INTO prj_perslidwerkplek
(prj_perslidwerkplek_key, prs_perslidwerkplek_key,
prs_perslid_key, prs_afdeling_key, prj_werkplek_key,
prj_perslidwerkplek_bezetting)
SELECT NULL, pwx.prs_perslidwerkplek_key, pwx.prs_perslid_key,
pwx.prs_afdeling_key, pwx.prj_werkplek_key,
pwx.prj_perslidwerkplek_bezetting
FROM prj_perslidwerkplek pwx,
prj_werkplek wx,
prj_ruimte rx
WHERE pwx.prj_werkplek_key = wx.prj_werkplek_key
AND rx.prj_scenario_key = pscenariokey_from
AND wx.prj_ruimte_key = rx.prj_ruimte_key;
*/
-- Kopieer de objecten
INSERT INTO prj_deel
(prj_deel_key, ins_deel_key, prj_ruimte_key,
prj_deel_omschrijving, ins_srtdeel_key)
SELECT NULL, dx.ins_deel_key, dx.prj_ruimte_key, dx.prj_deel_omschrijving,
dx.ins_srtdeel_key
FROM prj_deel dx, prj_ruimte rx
WHERE dx.prj_ruimte_key = rx.prj_ruimte_key
AND rx.prj_scenario_key = pscenariokey_from;
COMMIT;
END prj_copy_scenario;
PROCEDURE prj_reinitiate_scenario (
pscenariokey IN NUMBER,
pverdiepingkey IN NUMBER
)
IS
BEGIN
checkscenario (pscenariokey);
-- Oogmerk van deze routine kan het opfrissen van het snapshot van dit scenario zijn met behoud van reeds gedane wijzigingen
-- FUTURE EXTENSION
END prj_reinitiate_scenario;
-- Annuleer een scenario of een verdieping van een scenario
-- Als pverdiepingkey NULL is, wordt ook het scenario verwijderd.
PROCEDURE prj_cancel_scenario (
pscenariokey IN NUMBER,
pverdiepingkey IN NUMBER
)
IS
dummy VARCHAR2 (1);
BEGIN
checkscenario (pscenariokey);
IF pverdiepingkey IS NULL
THEN
DELETE FROM prj_ruimte rx
WHERE rx.prj_scenario_key = pscenariokey;
-- Deze cascadeert door naar de onderliggende items
DELETE FROM prj_scenario
WHERE prj_scenario_key = pscenariokey;
ELSE
-- Zet nu alle werkplekken die van een andere verdieping naar deze
-- te verwijderen verdieping gezet zijn terug naar waar ze vandaan kwamen
UPDATE prj_werkplek wx
SET wx.prj_ruimte_key =
(SELECT prj_ruimte_key
FROM prj_ruimte rx, alg_ruimte r, prs_werkplek w
WHERE wx.prs_werkplek_key = w.prs_werkplek_key
AND w.prs_alg_ruimte_key = r.alg_ruimte_key
AND rx.alg_ruimte_key = r.alg_ruimte_key
AND rx.prj_scenario_key = pscenariokey)
WHERE wx.prj_ruimte_key IN (
SELECT prj_ruimte_key
FROM prj_ruimte
WHERE alg_verdieping_key = pverdiepingkey
AND prj_scenario_key = pscenariokey);
-- De personen die van een andere verdieping op een werkplke zijn gezet die nu
-- gaat vervallen, komen tussen de thuislozen terecht. Terugzetten op hun oude plek
-- is nl. ook niet altijd triviaal. Het zou mooi zijn als ze nu vanuit dat reservoir
-- een nieuwe plek kunnen gaat krijgen.
-- Suggestie: dergelijke personen in de buffer gooien?
-- Vervolgens worden nu de ruimtekopien van de gevraagde verdieping weer verwijderd.
DELETE FROM prj_ruimte rx
WHERE rx.prj_scenario_key = pscenariokey
AND rx.alg_verdieping_key = pverdiepingkey;
END IF;
END prj_cancel_scenario;
----------------------------------------------
-- SCENARIO TRANSACTION PROCEDURES
----------------------------------------------
---------------------------------------
-- Moves a werkplek to another ruimte
---------------------------------------
PROCEDURE prj_move_werkplek (pwerkplekkey IN NUMBER, pruimtekey IN NUMBER)
IS
currentnr prj_werkplek.prj_werkplek_volgnr%TYPE;
werkpleknr prj_werkplek.prj_werkplek_volgnr%TYPE;
werkplekomschrijving prj_werkplek.prj_werkplek_omschrijving%TYPE;
scenariokey prj_ruimte.prj_scenario_key%TYPE;
BEGIN
SELECT prj_werkplek_volgnr
INTO currentnr
FROM prj_werkplek
WHERE prj_werkplek_key = pwerkplekkey;
werkpleknr :=
TO_NUMBER (forceuniqueness ('PRJ_WERKPLEK',
pruimtekey,
TO_CHAR (currentnr)
)
);
werkplekomschrijving := defaultwpomschrijving (pruimtekey, werkpleknr);
UPDATE prj_werkplek
SET prj_ruimte_key = pruimtekey,
prj_werkplek_volgnr = werkpleknr,
prj_werkplek_omschrijving = werkplekomschrijving
WHERE prj_werkplek_key = pwerkplekkey AND prj_ruimte_key <> pruimtekey;
-- niet onnodig moven
SELECT prj_scenario_key
INTO scenariokey
FROM prj_ruimte
WHERE prj_ruimte_key = pruimtekey;
END;
-------------------------------------
-- Find a sufficently free werkplek in ruimte pruimtekey
-- If necessary create a new one
-------------------------------------
FUNCTION find_or_create_free_werkplek (
pruimtekey IN NUMBER,
bezetting IN NUMBER
)
RETURN NUMBER
IS
omschrijving VARCHAR2 (30);
prefix VARCHAR2 (30);
werkplekkey prj_werkplek.prj_werkplek_key%TYPE;
werkpleknr prj_werkplek.prj_werkplek_volgnr%TYPE;
werkplekomschrijving prj_werkplek.prj_werkplek_omschrijving%TYPE;
BEGIN
BEGIN
-- Wat is de eerste werkplek in de nieuwe ruimte waarin deze bezetting zou passen?
SELECT prj_werkplek_key
INTO werkplekkey
FROM (SELECT wx.prj_werkplek_key
FROM (SELECT *
FROM prj_werkplek
WHERE prj_werkplek_verwijder IS NULL) wx,
(SELECT *
FROM prj_perslidwerkplek
WHERE prj_perslidwerkplek_verwijder IS NULL) pwx
WHERE wx.prj_ruimte_key = pruimtekey
AND wx.prj_werkplek_key = pwx.prj_werkplek_key(+)
GROUP BY wx.prj_werkplek_key
HAVING NVL (SUM (pwx.prj_perslidwerkplek_bezetting), 0)
+ bezetting <= 100)
WHERE ROWNUM = 1;
EXCEPTION
WHEN NO_DATA_FOUND
THEN
-- Zo nee: verzin er eentje (begin bij 901 te tellen)
werkpleknr :=
TO_NUMBER (forceuniqueness ('PRJ_WERKPLEK',
pruimtekey,
TO_CHAR (901)
)
);
werkplekomschrijving :=
defaultwpomschrijving (pruimtekey, werkpleknr);
INSERT INTO prj_werkplek
(prj_werkplek_key, prs_werkplek_key,
prj_werkplek_volgnr, prj_werkplek_omschrijving,
prj_werkplek_vastopp, prj_ruimte_key
)
VALUES (NULL, NULL,
werkpleknr, werkplekomschrijving,
NULL, pruimtekey
);
SELECT prj_werkplek_key
INTO werkplekkey
FROM prj_werkplek
WHERE prj_ruimte_key = pruimtekey
AND prj_werkplek_volgnr = werkpleknr;
--DBMS_OUTPUT.put_line ('inserted werkplekkey:' || TO_CHAR (werkplekkey));
END;
RETURN werkplekkey;
END; -- Function find_or_create_free_werkplek
-------------------------------------
-- Moves a perslidwerkplek (bezetting) to another ruimte/werkplek. The old werkplek remains
-- pwerkplekkey is optional and acts like a preferred werkplek and will be used if it fits.
-------------------------------------
PROCEDURE prj_move_perslidwerkplek (
pperslidwerkplekkey IN NUMBER,
pruimtekey IN NUMBER,
pwerkplekkey IN NUMBER
)
IS
oldruimtekey prj_werkplek.prj_ruimte_key%TYPE;
oldwerkplekkey prj_werkplek.prj_werkplek_key%TYPE;
currentbezetting prj_perslidwerkplek.prj_perslidwerkplek_bezetting%TYPE;
reedsbezet prj_perslidwerkplek.prj_perslidwerkplek_bezetting%TYPE;
scenariokey prj_ruimte.prj_scenario_key%TYPE;
werkplekkey prj_werkplek.prj_werkplek_key%TYPE;
BEGIN
werkplekkey := -1;
-- Wat is eigenlijk de ruimte/werkplek van herkomst en de actuele bezetting van de te verplaatsen werkplek?
SELECT wx.prj_ruimte_key, pwx.prj_perslidwerkplek_bezetting,
wx.prj_werkplek_key
INTO oldruimtekey, currentbezetting,
oldwerkplekkey
FROM prj_werkplek wx, prj_perslidwerkplek pwx
WHERE wx.prj_werkplek_key = pwx.prj_werkplek_key
AND pwx.prj_perslidwerkplek_key = pperslidwerkplekkey;
--DBMS_OUTPUT.put_line ('oldruimtekey:' || TO_CHAR (oldruimtekey));
--DBMS_OUTPUT.put_line ('currentbezetting:' || TO_CHAR (currentbezetting));
IF pwerkplekkey IS NOT NULL AND pwerkplekkey = oldwerkplekkey
THEN
prj_log_add
( 'Werkplekbezetting niet verplaatst (zelfde werkplekkey='
|| TO_CHAR (oldwerkplekkey)
|| ')',
'MOVE',
scenariokey
);
RETURN;
END IF;
IF pwerkplekkey IS NOT NULL
THEN
-- Voldoet de meegegeven voorkeurswerkplek?
SELECT NVL (SUM (pwx.prj_perslidwerkplek_bezetting), 0)
INTO reedsbezet
FROM prj_perslidwerkplek pwx
WHERE pwx.prj_werkplek_key = pwerkplekkey
AND prj_perslidwerkplek_verwijder IS NULL;
-- meegegeven werkplek past en is bepaald in werkplekkey
IF reedsbezet + currentbezetting <= 100
THEN
werkplekkey := pwerkplekkey;
END IF;
END IF;
-- Is de bestemmingsruimte een andere dan de huidige?
IF pruimtekey = oldruimtekey AND werkplekkey = -1
THEN
prj_log_add
( 'Werkplekbezetting niet verplaatst (zelfde ruimtekey='
|| TO_CHAR (oldruimtekey)
|| ')',
'MOVE',
scenariokey
);
RETURN;
END IF;
IF werkplekkey = -1
THEN
werkplekkey :=
find_or_create_free_werkplek (pruimtekey, currentbezetting);
END IF;
-- Er is nu een werkplekkey bepaald.
UPDATE prj_perslidwerkplek
SET prj_werkplek_key = werkplekkey
WHERE prj_perslidwerkplek_key = pperslidwerkplekkey
AND prj_werkplek_key <> werkplekkey;
-- niet onnodig moven (dubbelcheck)
COMMIT;
END;
-------------------------------------
-- Moves a perslid to a ruimte/werkplek. There was no previous
-- pwerkplekkey is optional and acts like a preferred werkplek and will be used if it fits.
-------------------------------------
PROCEDURE prj_move_perslid (
pperslidkey IN NUMBER,
pruimtekey IN NUMBER,
pwerkplekkey IN NUMBER
)
IS
reedsbezet prj_perslidwerkplek.prj_perslidwerkplek_bezetting%TYPE;
doelbezetting prj_perslidwerkplek.prj_perslidwerkplek_bezetting%TYPE;
werkplekkey prj_werkplek.prj_werkplek_key%TYPE;
werkpleknr prj_werkplek.prj_werkplek_volgnr%TYPE;
werkplekomschrijving prj_werkplek.prj_werkplek_omschrijving%TYPE;
scenariokey prj_ruimte.prj_scenario_key%TYPE;
BEGIN
werkplekkey := -1;
-- Wat is de te gebruiken bezetting van deze persoon (100 minus reeds op andere plekken aanwezig)?
SELECT 100 - NVL (SUM (pwx.prj_perslidwerkplek_bezetting), 0)
INTO doelbezetting
FROM prj_perslidwerkplek pwx, prj_werkplek pw
WHERE pwx.prs_perslid_key = pperslidkey
AND pw.prj_ruimte_key = pruimtekey
AND pwx.prj_werkplek_key = pw.prj_werkplek_key
AND prj_perslidwerkplek_verwijder IS NULL;
IF pwerkplekkey IS NOT NULL
THEN
-- Voldoet de meegegeven voorkeurswerkplek?
SELECT NVL (SUM (pwx.prj_perslidwerkplek_bezetting), 0)
INTO reedsbezet
FROM prj_perslidwerkplek pwx
WHERE pwx.prj_werkplek_key = pwerkplekkey
AND prj_perslidwerkplek_verwijder IS NULL;
-- meegegeven werkplek past en is bepaald in werkplekkey
IF reedsbezet + doelbezetting <= 100
THEN
werkplekkey := pwerkplekkey;
END IF;
END IF;
IF werkplekkey = -1
THEN
werkplekkey :=
find_or_create_free_werkplek (pruimtekey, doelbezetting);
END IF;
--DBMS_OUTPUT.put_line ('werkplekkey:' || TO_CHAR (werkplekkey));
-- Er is nu een werkplekkey bepaald.
INSERT INTO prj_perslidwerkplek
(prj_werkplek_key, prs_perslid_key,
prj_perslidwerkplek_bezetting
)
VALUES (werkplekkey, pperslidkey,
doelbezetting
);
COMMIT;
END;
----------------------------------------------
-- SCENARIO COMMIT PROCEDURES
----------------------------------------------
PROCEDURE prj_commit_additions (pscenariokey IN NUMBER)
IS
CURSOR new_ruimte (sk IN NUMBER)
IS
SELECT alg_verdieping_key, prj_ruimte_nr, prj_ruimte_omschrijving,
prj_ruimte_bruto_vloeropp, alg_srtruimte_key,
prj_ruimte_omtrek, prj_ruimte_inhoud, prj_ruimte_opmerking,
prj_ruimte_key
FROM prj_ruimte rx
WHERE rx.prj_ruimte_verwijder IS NULL
AND rx.alg_ruimte_key IS NULL
AND rx.prj_scenario_key = sk;
CURSOR new_werkplek (sk IN NUMBER)
IS
SELECT prj_werkplek_volgnr, prj_werkplek_omschrijving,
prj_werkplek_vastopp, prj_werkplek_opp, rx.alg_ruimte_key,
prj_werkplek_key
FROM prj_werkplek wx, prj_ruimte rx
WHERE wx.prj_werkplek_verwijder IS NULL
AND wx.prs_werkplek_key IS NULL
AND rx.prj_ruimte_key = wx.prj_ruimte_key
AND rx.prj_scenario_key = sk;
CURSOR new_perslidwerkplek (sk IN NUMBER)
IS
SELECT prs_perslid_key, prs_afdeling_key, prs_werkplek_key,
prj_perslidwerkplek_bezetting, pwx.prj_perslidwerkplek_key
FROM prj_perslidwerkplek pwx, prj_werkplek wx, prj_ruimte rx
WHERE pwx.prj_perslidwerkplek_verwijder IS NULL
AND pwx.prs_perslidwerkplek_key IS NULL
AND wx.prj_werkplek_key = pwx.prj_werkplek_key
AND rx.prj_ruimte_key = wx.prj_ruimte_key
AND rx.prj_scenario_key = sk;
CURSOR new_deel (sk IN NUMBER)
IS
SELECT dx.prj_deel_key
FROM prj_deel dx, prj_werkplek wx, prj_ruimte rx
WHERE dx.prj_deel_verwijder IS NULL
AND dx.ins_deel_key IS NULL
AND wx.prj_werkplek_key = dx.prj_werkplek_key
AND dx.prj_werkplek_key IS NOT NULL
AND rx.prj_ruimte_key = wx.prj_ruimte_key
AND rx.prj_scenario_key = sk
UNION ALL
SELECT dx.prj_deel_key
FROM prj_deel dx, prj_werkplek wx, prj_ruimte rx
WHERE dx.prj_deel_verwijder IS NULL
AND dx.ins_deel_key IS NULL
AND dx.prj_werkplek_key IS NULL
AND rx.prj_ruimte_key = wx.prj_ruimte_key
AND rx.prj_scenario_key = sk;
aantal_r_toegevoegd NUMBER;
aantal_w_toegevoegd NUMBER;
aantal_pw_toegevoegd NUMBER;
aantal_d_toegevoegd NUMBER;
ruimte_nr alg_ruimte.alg_ruimte_nr%TYPE;
werkplek_nr prs_werkplek.prs_werkplek_volgnr%TYPE;
deel_nr ins_deel.ins_deel_omschrijving%TYPE;
BEGIN
-- Nieuwe ruimtes toevoegen
aantal_r_toegevoegd := 0;
--
-- RUIMTES
--
FOR v_ruimte IN new_ruimte (pscenariokey)
LOOP
ruimte_nr :=
forceuniqueness ('ALG_RUIMTE',
v_ruimte.alg_verdieping_key,
v_ruimte.prj_ruimte_nr
);
INSERT INTO alg_ruimte r
(alg_verdieping_key, alg_ruimte_nr,
alg_ruimte_omschrijving,
alg_ruimte_bruto_vloeropp,
alg_srtruimte_key, alg_ruimte_omtrek,
alg_ruimte_inhoud,
alg_ruimte_opmerking
)
VALUES (v_ruimte.alg_verdieping_key, ruimte_nr,
v_ruimte.prj_ruimte_omschrijving,
v_ruimte.prj_ruimte_bruto_vloeropp,
v_ruimte.alg_srtruimte_key, v_ruimte.prj_ruimte_omtrek,
v_ruimte.prj_ruimte_inhoud,
v_ruimte.prj_ruimte_opmerking
);
aantal_r_toegevoegd := aantal_r_toegevoegd + 1;
-- Registreer de zojuist verworven key; deze is nodig voor de volgende stappen
UPDATE prj_ruimte rx
SET alg_ruimte_key =
(SELECT alg_ruimte_key
FROM alg_v_aanwezigruimte r
WHERE r.alg_verdieping_key = v_ruimte.alg_verdieping_key
AND r.alg_ruimte_nr = ruimte_nr)
WHERE prj_ruimte_key = v_ruimte.prj_ruimte_key;
END LOOP;
--
-- WERKPLEKKEN
--
aantal_w_toegevoegd := 0;
FOR v_werkplek IN new_werkplek (pscenariokey)
LOOP
werkplek_nr :=
forceuniqueness ('PRS_WERKPLEK',
v_werkplek.alg_ruimte_key,
TO_CHAR (v_werkplek.prj_werkplek_volgnr)
);
-- Note: de omschrijving is meestal ruimtenr+volgnr. Bij nieuwe of verplaatsing is het wenselijk deza aan te passen?
--werkpleknr := to_number(substr(Omschrijving,instr(Omschrijving,'-',1)+1));
INSERT INTO prs_werkplek w
(prs_werkplek_volgnr, prs_werkplek_omschrijving,
prs_werkplek_vastopp,
prs_werkplek_opp, prs_alg_ruimte_key
)
VALUES (werkplek_nr, v_werkplek.prj_werkplek_omschrijving,
v_werkplek.prj_werkplek_vastopp,
v_werkplek.prj_werkplek_opp, v_werkplek.alg_ruimte_key
);
aantal_w_toegevoegd := aantal_w_toegevoegd + 1;
-- Registreer de zojuist verworven keys; deze zijn nodig voor de volgende stappen
UPDATE prj_werkplek wx
SET prs_werkplek_key =
(SELECT prs_werkplek_key
FROM prs_v_aanwezigwerkplek w
WHERE w.prs_werkplek_volgnr = werkplek_nr
AND w.prs_alg_ruimte_key = v_werkplek.alg_ruimte_key)
WHERE prj_werkplek_key = v_werkplek.prj_werkplek_key;
END LOOP;
--
-- WERKPLEKBEZETTINGEN (anoniem)
--
aantal_pw_toegevoegd := 0;
FOR v_perslidwerkplek IN new_perslidwerkplek (pscenariokey)
LOOP
INSERT INTO prs_perslidwerkplek pw
(prs_perslid_key,
prs_afdeling_key,
prs_werkplek_key,
prs_perslidwerkplek_bezetting
)
VALUES (v_perslidwerkplek.prs_perslid_key,
v_perslidwerkplek.prs_afdeling_key,
v_perslidwerkplek.prs_werkplek_key,
v_perslidwerkplek.prj_perslidwerkplek_bezetting
);
-- Bijwerken van de nieuwe keys is niet nodig..
aantal_pw_toegevoegd := aantal_pw_toegevoegd + 1;
END LOOP;
--
-- OBJECTEN
--
aantal_d_toegevoegd := 0;
-- FOR v_deel IN new_deel (pscenariokey)
-- LOOP
-- deel_nr := forceuniqueness ('INS_DEEL', v_deel.ins_alg_locatie_key, v_deel.ins_deel_omschrijving);
--
-- INSERT INTO ins_deel
-- (ins_srtdeel_key, ins_alg_ruimte_key, ins_alg_ruimte_type,
-- ins_alg_locatie_key, ins_discipline_key, ins_deel_omschrijving, ins_deel_parent_key,
-- ins_deel_oppervlak, ins_deel_omtrek, ins_deel_getekend, ins_deel_verwijder
-- )
-- VALUES (v_deel.ins_srtdeel_key, v_deel.prj_ruimte_key, v_deel.ins_alg_ruimte_type,
-- v_deel.ins_alg_locatie_key, v_deel.ins_discipline_key, omschrijving, v_deel.ins_deel_parent_key,
-- v_deel.ins_deel_oppervlak, v_deel.ins_deel_omtrek
-- );
-- -- Bijwerken van de nieuwe keys is niet nodig..
-- aantal_d_toegevoegd := aantal_d_toegevoegd + 1;
-- END LOOP;
prj_log_add ('Nieuwe ruimtes : ' || TO_CHAR (aantal_r_toegevoegd),
'123',
pscenariokey
);
prj_log_add ('Nieuwe werkplekken: ' || TO_CHAR (aantal_w_toegevoegd),
'123',
pscenariokey
);
prj_log_add ('Nieuwe objecten: ' || TO_CHAR (aantal_d_toegevoegd),
'123',
pscenariokey
);
prj_log_add ('Nieuwe bezettingen: ' || TO_CHAR (aantal_pw_toegevoegd),
'123',
pscenariokey
);
END prj_commit_additions;
PROCEDURE prj_commit_changes (pscenariokey IN NUMBER)
IS
CURSOR ruimte_updates (sk IN NUMBER)
IS
SELECT prj_ruimte_nr, prj_ruimte_omschrijving,
prj_ruimte_bruto_vloeropp, alg_srtruimte_key,
prj_ruimte_omtrek, prj_ruimte_inhoud, prj_ruimte_opmerking,
alg_ruimte_key
FROM prj_ruimte rx
WHERE rx.prj_ruimte_verwijder IS NULL
AND rx.alg_ruimte_key IS NOT NULL
AND rx.prj_scenario_key = sk;
CURSOR werkplek_updates (sk IN NUMBER)
IS
SELECT prj_werkplek_volgnr, prj_werkplek_omschrijving,
prj_werkplek_vastopp, prj_werkplek_opp,
prs_werkplek_key, alg_ruimte_key
FROM prj_werkplek wp, prj_ruimte rx
WHERE wp.prj_ruimte_key = rx.prj_ruimte_key
AND wp.prj_werkplek_verwijder IS NULL
AND wp.prs_werkplek_key IS NOT NULL
AND rx.prj_scenario_key = sk;
CURSOR perslidwerkplek_updates (sk IN NUMBER)
IS
SELECT prs_perslid_key, prs_afdeling_key,
prj_perslidwerkplek_bezetting,
prs_perslidwerkplek_key, prs_werkplek_key
FROM prj_perslidwerkplek pwp, prj_werkplek wp, prj_ruimte rx
WHERE pwp.prj_werkplek_key = wp.prj_werkplek_key
AND wp.prj_ruimte_key = rx.prj_ruimte_key
AND wp.prj_werkplek_verwijder IS NULL
AND wp.prs_werkplek_key IS NOT NULL
AND rx.prj_scenario_key = sk;
BEGIN
BEGIN
-- Bestaande ruimtes aanpassen
FOR cr IN ruimte_updates (pscenariokey)
LOOP
UPDATE alg_ruimte r
SET alg_ruimte_nr = cr.prj_ruimte_nr,
alg_ruimte_omschrijving = cr.prj_ruimte_omschrijving,
alg_ruimte_bruto_vloeropp = cr.prj_ruimte_bruto_vloeropp,
alg_srtruimte_key = cr.alg_srtruimte_key,
alg_ruimte_omtrek = cr.prj_ruimte_omtrek,
alg_ruimte_inhoud = cr.prj_ruimte_inhoud,
alg_ruimte_opmerking = cr.prj_ruimte_opmerking
WHERE r.alg_ruimte_verwijder IS NULL
AND r.alg_ruimte_key = cr.alg_ruimte_key;
END LOOP;
-- Bestaande werkplekken aanpassen
FOR cr IN werkplek_updates (pscenariokey)
LOOP
UPDATE prs_werkplek r
SET prs_alg_ruimte_key = cr.alg_ruimte_key,
prs_werkplek_volgnr = cr.prj_werkplek_volgnr,
prs_werkplek_omschrijving = cr.prj_werkplek_omschrijving,
prs_werkplek_vastopp = cr.prj_werkplek_vastopp,
prs_werkplek_opp = cr.prj_werkplek_opp
WHERE r.prs_werkplek_verwijder IS NULL
AND r.prs_werkplek_key = cr.prs_werkplek_key;
END LOOP;
-- Bestaande perslidwerkplekken aanpassen
FOR cr IN perslidwerkplek_updates (pscenariokey)
LOOP
UPDATE prs_perslidwerkplek r
SET prs_werkplek_key = cr.prs_werkplek_key,
prs_perslid_key = cr.prs_perslid_key,
-- prs_afdeling_key = cr.prs_afdeling_key,
prs_perslidwerkplek_bezetting = cr.prj_perslidwerkplek_bezetting
WHERE r.prs_perslidwerkplek_verwijder IS NULL
AND r.prs_perslidwerkplek_key = cr.prs_perslidwerkplek_key;
END LOOP;
END;
END prj_commit_changes;
PROCEDURE prj_commit_deletions (pscenariokey IN NUMBER)
IS
BEGIN
-- Vervallen ruimtes laten vervallen
UPDATE alg_ruimte r
SET alg_ruimte_verwijder =
(SELECT SYSDATE
FROM prj_ruimte rx
WHERE rx.alg_ruimte_key = r.alg_ruimte_key
AND rx.prj_ruimte_verwijder IS NOT NULL
AND rx.alg_ruimte_key IS NOT NULL
AND rx.prj_scenario_key = pscenariokey)
WHERE r.alg_ruimte_verwijder IS NULL;
-- Vervallen werkplekken laten vervallen
UPDATE prs_werkplek p
SET prs_werkplek_verwijder =
(SELECT SYSDATE
FROM prj_werkplek pw, prj_ruimte rx
WHERE pw.prj_ruimte_key = rx.prj_ruimte_key
AND pw.prs_werkplek_key = p.prs_werkplek_key
AND pw.prj_werkplek_verwijder IS NOT NULL
AND pw.prs_werkplek_key IS NOT NULL
AND rx.prj_scenario_key = pscenariokey)
WHERE p.prs_werkplek_verwijder IS NULL;
-- Vervallen perslidwerkplekken laten vervallen
UPDATE prs_perslidwerkplek p
SET prs_perslidwerkplek_verwijder =
(SELECT SYSDATE
FROM prj_perslidwerkplek ppw, prj_werkplek pw, prj_ruimte rx
WHERE ppw.prj_werkplek_key = pw.prj_werkplek_key
AND pw.prj_ruimte_key = rx.prj_ruimte_key
AND ppw.prs_perslidwerkplek_key = p.prs_perslidwerkplek_key
AND ppw.prj_perslidwerkplek_verwijder IS NOT NULL
AND ppw.prs_perslidwerkplek_key IS NOT NULL
AND rx.prj_scenario_key = pscenariokey)
WHERE p.prs_perslidwerkplek_verwijder IS NULL;
END prj_commit_deletions;
PROCEDURE prj_commit_cleanup (pscenariokey IN NUMBER)
IS
requestkey prj_scenario.mld_melding_key%TYPE;
BEGIN
-- Voor welke aanvraag was dit scenario een oplossing?
SELECT mld_melding_key
INTO requestkey
FROM prj_scenario
WHERE prj_scenario_key = pscenariokey;
-- IF requestkey IS NOT NULL
-- THEN
-- DELETE FROM prj_scenario
-- WHERE prj_scenario_key IN (SELECT prj_scenario_key
-- FROM prj_scenario
-- WHERE mld_melding_key = requestkey);
--
-- END IF;
END prj_commit_cleanup;
PROCEDURE prj_commit_scenario (pscenariokey IN NUMBER)
IS
dummy VARCHAR2 (1);
BEGIN
checkscenario (pscenariokey);
prj_commit_additions (pscenariokey);
prj_commit_changes (pscenariokey);
prj_commit_deletions (pscenariokey);
prj_commit_cleanup (pscenariokey);
END prj_commit_scenario;
END prj;
/
#endif
#endif // PRJ