179 lines
5.3 KiB
SAS
179 lines
5.3 KiB
SAS
/**
|
|
@file
|
|
@brief Testing mpe_targetloader macro - REPLACE loadtype
|
|
@details Covers the REPLACE branch of mpe_targetloader.sas:
|
|
|
|
* LOADTARGET=NO (diff screen preparation) - all staged records classed as
|
|
new, all existing records classed as deleted, target table unchanged
|
|
* LOADTARGET=YES (actual load) - target table fully replaced by the
|
|
staging table, delete flag column dropped, processed column stamped,
|
|
per-record delete flags ignored (everything is loaded)
|
|
|
|
A dedicated DCTEST.DC_REPLACE table is registered in MPE_TABLES (and the
|
|
registration removed again in cleanup). The DCTEST library is BASE engine,
|
|
so the CAS-specific branch (deleteRows truncation / varchar casting) is not
|
|
exercised here.
|
|
|
|
<h4> SAS Macros </h4>
|
|
@li mp_assert.sas
|
|
@li mp_assertdsobs.sas
|
|
@li mp_assertscope.sas
|
|
@li mpe_targetloader.sas
|
|
|
|
@author 4GL Apps Ltd
|
|
@copyright 4GL Apps Ltd. This code may only be used within Data Controller
|
|
and may not be re-distributed or re-sold without the express permission of
|
|
4GL Apps Ltd.
|
|
**/
|
|
|
|
%let syscc=0;
|
|
|
|
/**
|
|
* Prep - physical target table and MPE_TABLES registration
|
|
*/
|
|
data dctest.dc_replace;
|
|
length pk $8 val $20;
|
|
pk='OLD1'; val='oldvalue1'; processed_dttm=0; output;
|
|
pk='OLD2'; val='oldvalue2'; processed_dttm=0; output;
|
|
format processed_dttm datetime19.;
|
|
run;
|
|
|
|
proc sql noprint;
|
|
delete from &dc_libref..mpe_tables where libref="DCTEST" and dsn='DC_REPLACE';
|
|
insert into &dc_libref..mpe_tables
|
|
set tx_from=0
|
|
,tx_to='31DEC5999:23:59:59'dt
|
|
,libref="DCTEST"
|
|
,dsn='DC_REPLACE'
|
|
,buskey='PK'
|
|
,loadtype='REPLACE'
|
|
,var_processed='PROCESSED_DTTM'
|
|
,num_of_approvals_required=1;
|
|
quit;
|
|
|
|
/* staging table, as it would arrive from the approval package */
|
|
data work.staging_ds;
|
|
length pk $8 val $20 _____DELETE__THIS__RECORD_____ $3;
|
|
pk='NEW1'; val='newvalue1'; _____DELETE__THIS__RECORD_____='No'; output;
|
|
pk='NEW2'; val='newvalue2'; _____DELETE__THIS__RECORD_____='Yes'; output;
|
|
pk='NEW3'; val='newvalue3'; _____DELETE__THIS__RECORD_____='No'; output;
|
|
run;
|
|
|
|
/**
|
|
* Test 1 - LOADTARGET=NO builds the diff tables without touching the target
|
|
*/
|
|
%mp_assertscope(SNAPSHOT)
|
|
%mpe_targetloader(libds=DCTEST.DC_REPLACE
|
|
,etlsource=mpe_targetloader.test
|
|
,STAGING_DS=STAGING_DS
|
|
,LOADTARGET=NO
|
|
,dclib=&dc_libref
|
|
,dc_dttmtfmt=&dc_dttmtfmt.
|
|
)
|
|
%mp_assertscope(COMPARE,
|
|
desc=%str(Test 1 - checking macro variables against previous snapshot)
|
|
)
|
|
|
|
%mp_assert(iftrue=(&syscc=0),
|
|
desc=%str(Test 1 - REPLACE LOADTARGET=NO completed without errors),
|
|
outds=work.test_results
|
|
)
|
|
|
|
%mp_assertdsobs(work.outds_add,
|
|
desc=%str(Test 1 - all staged records classed as new),
|
|
test=EQUALS 3,
|
|
outds=work.test_results
|
|
)
|
|
%mp_assertdsobs(work.outds_del,
|
|
desc=%str(Test 1 - all existing records classed as deleted),
|
|
test=EQUALS 2,
|
|
outds=work.test_results
|
|
)
|
|
%mp_assertdsobs(work.outds_mod,
|
|
desc=%str(Test 1 - no records classed as modified),
|
|
test=EQUALS 0,
|
|
outds=work.test_results
|
|
)
|
|
%mp_assertdsobs(dctest.dc_replace,
|
|
desc=%str(Test 1 - target table not modified),
|
|
test=EQUALS 2,
|
|
outds=work.test_results
|
|
)
|
|
|
|
/**
|
|
* Test 2 - LOADTARGET=YES replaces the target table with the staged data
|
|
*/
|
|
%mp_assertscope(SNAPSHOT)
|
|
%mpe_targetloader(libds=DCTEST.DC_REPLACE
|
|
,etlsource=mpe_targetloader.test
|
|
,STAGING_DS=STAGING_DS
|
|
,LOADTARGET=YES
|
|
,dclib=&dc_libref
|
|
,dc_dttmtfmt=&dc_dttmtfmt.
|
|
)
|
|
%mp_assertscope(COMPARE,
|
|
desc=%str(Test 2 - checking macro variables against previous snapshot)
|
|
)
|
|
|
|
%mp_assert(iftrue=(&syscc=0),
|
|
desc=%str(Test 2 - REPLACE LOADTARGET=YES completed without errors),
|
|
outds=work.test_results
|
|
)
|
|
|
|
%mp_assertdsobs(dctest.dc_replace,
|
|
desc=%str(Test 2 - target row count matches staging table),
|
|
test=EQUALS 3,
|
|
outds=work.test_results
|
|
)
|
|
|
|
proc sql noprint;
|
|
select count(*) into: oldrows
|
|
from dctest.dc_replace where pk in ('OLD1','OLD2');
|
|
select count(*) into: newrows
|
|
from dctest.dc_replace where pk in ('NEW1','NEW2','NEW3');
|
|
select count(*) into: delcol from dictionary.columns
|
|
where libname='DCTEST' and memname='DC_REPLACE'
|
|
and upcase(name)='_____DELETE__THIS__RECORD_____';
|
|
select count(*) into: notstamped
|
|
from dctest.dc_replace where missing(processed_dttm) or processed_dttm=0;
|
|
quit;
|
|
|
|
%mp_assert(iftrue=(&oldrows=0),
|
|
desc=%str(Test 2 - pre-existing records removed from target),
|
|
outds=work.test_results
|
|
)
|
|
%mp_assert(iftrue=(&newrows=3),
|
|
desc=%str(Test 2 - all staged records loaded, delete flags ignored),
|
|
outds=work.test_results
|
|
)
|
|
%mp_assert(iftrue=(&delcol=0),
|
|
desc=%str(Test 2 - delete flag column not loaded to target),
|
|
outds=work.test_results
|
|
)
|
|
%mp_assert(iftrue=(¬stamped=0),
|
|
desc=%str(Test 2 - processed_dttm stamped on every loaded record),
|
|
outds=work.test_results
|
|
)
|
|
|
|
/**
|
|
* Cleanup - remove all persistent state created by this test, so that a
|
|
* subsequent run starts from the same position (including a run that
|
|
* previously failed partway through)
|
|
*/
|
|
proc sql noprint;
|
|
/* REPLACE table registration */
|
|
delete from &dc_libref..mpe_tables where libref="DCTEST" and dsn='DC_REPLACE';
|
|
/* lock record (may be left as LOCKED after an aborted run) */
|
|
delete from &dc_libref..mpe_lockanytable
|
|
where lock_lib="DCTEST" and lock_ds="DC_REPLACE";
|
|
quit;
|
|
|
|
/* physical target table */
|
|
proc datasets lib=dctest nolist;
|
|
delete dc_replace;
|
|
run;
|
|
quit;
|
|
|
|
/* assertion macro variables */
|
|
%symdel oldrows newrows delcol notstamped;
|