I have two tables, CUSTOMER.ACCOUNTS and CUSTOMER.RELATION****PS, as
follows:
CREATE TABLE "CUSTOMER"."ACCOUNTS" (
"ACCOUNT_ID" DECIMAL(12,0) NOT NULL GENERATED ALWAYS AS IDENTITY (
START WITH +0 INCREMENT BY +1 MINVALUE +1 MAXVALUE +999999999999
NO CYCLE CACHE 20 NO ORDER ) ,
"APPL_CODE" CHAR(3) NOT NULL ,
"APPL_ID" DECIMAL(16,0) NOT NULL ,
"BRANCH_NUMBER" DECIMAL(3,0) NOT NULL ,
"ADDRESS_KEY" DECIMAL(3,0) NOT NULL ,
"CATEGORY_CODE" CHAR(1) NOT NULL ,
"OPEN_DATE" DATE NOT NULL ,
"CLOSED_DATE" DATE ,
"PMT_APPL_CODE" CHAR(3) ,
"PMT_APPL_ID" DECIMAL(16,0) ,
"LAST_MTCE_DATE" DATE ,
"LAST_MTCE_YN" CHAR(1) NOT NULL WITH DEFAULT 'N' ,
"LAST_UPDATE" TIMESTAMP NOT NULL GENERATED ALWAYS FOR EACH ROW ON
UPDATE
AS ROW CHANGE TIMESTAMP )
IN "CUSTOMERR01" ;
-- DDL Statements for primary key on Table "CUSTOMER"."ACCOUNTS"
ALTER TABLE "CUSTOMER"."ACCOUNTS"
ADD CONSTRAINT "ACCOUNTS_PK" PRIMARY KEY
("ACCOUNT_ID");
-- DDL Statements for check constraints on Table "CUSTOMER"."ACCOUNTS"
ALTER TABLE "CUSTOMER"."ACCOUNTS"
ADD CONSTRAINT "ACCOUNTS_CK1" CHECK
("CUSTOMER"."ACCOUNTS"."LAST_MTCE_YN" in ('Y','N'))
ENFORCED
ENABLE QUERY OPTIMIZATION;
------------------------------------------------
-- DDL Statements for table "CUSTOMER"."ACCOUNT_RELATION****PS"
------------------------------------------------
CREATE TABLE "CUSTOMER"."ACCOUNT_RELATION****PS" (
"ACCOUNT_REL_ID" DECIMAL(12,0) NOT NULL GENERATED ALWAYS AS IDENTITY (
START WITH +0 INCREMENT BY +1 MINVALUE +1 MAXVALUE +999999999999
NO CYCLE CACHE 20 NO ORDER ) ,
"ACCOUNT_ID" DECIMAL(12,0) NOT NULL ,
"CIF_NUMBER" DECIMAL(9,0) NOT NULL ,
"RELATION****P_IND" CHAR(4) NOT NULL ,
"ADDED_DATE" DATE NOT NULL ,
"LAST_UPDATE" TIMESTAMP NOT NULL GENERATED ALWAYS FOR EACH ROW ON
UPDATE
AS ROW CHANGE TIMESTAMP )
IN "CUSTOMERR01" ;
-- DDL Statements for primary key on Table
"CUSTOMER"."ACCOUNT_RELATION****PS"
ALTER TABLE "CUSTOMER"."ACCOUNT_RELATION****PS"
ADD CONSTRAINT "ACCOUNT_REL_PK" PRIMARY KEY
("ACCOUNT_REL_ID");
-- DDL Statements for foreign keys on Table
"CUSTOMER"."ACCOUNT_RELATION****PS"
ALTER TABLE "CUSTOMER"."ACCOUNT_RELATION****PS"
ADD CONSTRAINT "ACCOUNTS_ACCT_REL_FK" FOREIGN KEY
("ACCOUNT_ID")
REFERENCES "CUSTOMER"."ACCOUNTS"
("ACCOUNT_ID")
ON DELETE NO ACTION
ON UPDATE NO ACTION
ENFORCED
ENABLE QUERY OPTIMIZATION;
There will be one or more customers (CIF_NUMBER) related to a particular
account_id in the CUSTOMER.ACCOUNTS table.
The business rules allow for only one account relation****p where the
relation****p_ind is 'EN' or 'BSIR' or 'DA' or 'FD%'. There are other
possible relation****ps, but they don't pertain to this issue.
Anyway, we are trying to determine which customer record will be used as
the
mailing address for the account. Here are the business rules:
No account can be related to more than one of the following: 'EN', 'BSIR',
'FD%'.
However an account *can* have an 'EN' and a 'DA' relation****p.
'DA' by itself is not allowed; there must also be an 'EN' relation****p.
If there is a 'DA' or a 'BSIR' relation****p, use the address of that
customer.
If there is a relation****p starting with 'FD', use the address of that
customer.
Otherwise use the address of the 'EN' customer.
So I created this function:
create function addr_cif (acct_id decimal(12))
returns decimal(9)
specific addr_cif_for_account
language sql
reads sql data
no external action
not deterministic
return
select cif_number
from customer.accounts as a
join customer.account_relation****ps as ar
on a.account_id = ar.account_id
where a.account_id = acct_id
and (ar.relation****p_ind in ('DA', 'BSIR')
or ar.relation****p_ind like 'FD%'
or (ar.relation****p_ind = 'EN'
and not exists (
select *
from customer.account_relation****ps
where account_id = acct_id
and relation****p_ind = 'DA'
)
)
)
@[EMAIL PROTECTED]
I can do something like this:
SELECT CIF_NUMBER
, RELATION****P_IND
, ADDRESS_KEY
FROM CUSTOMER.ACCOUNT_RELATION****PS AS ar
JOIN CUSTOMER.ACCOUNTS AS a
ON ar.ACCOUNT_ID = a.ACCOUNT_ID
WHERE APPL_CODE = 'SBX'
AND BRANCH_NUMBER = 375
AND APPL_ID = 38
AND CIF_NUMBER = ADDR_CIF(ar.ACCOUNT_ID);
In this case safebox 38 for branch 375 has three customers related to it.
One is related as 'EN' one as 'DA' and one as 'JP'.
This query properly returns the value of cif_number for the customer with
the 'DA' relation****p. If I remove the 'DA' related customer it returns
the
'EN' customer.
I don't know if it's overly complex though. Can it be simplified?
Any comments are welcome. I hope I was clear enough on the business
rules!
Thanks,
Frank


|