/**
  @file viewlibs.sas
  @brief List the libraries for view access
  @details

  <h4> SAS Macros </h4>
  @li dc_getlibs.sas
  @li mp_abort.sas
  @li mf_getuser.sas
  @li mpe_getgroups.sas
  @li mpeinit.sas

  @version 9.3
  @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.
**/

%mpeinit()

/**
  * get full list of libraries
  */
%dc_getlibs(outds=work.mm_getLibs)

/* get security groups */
%mpe_getgroups(user=%mf_getuser(),outds=groups)

/* get security settings */
data sec;
  set &mpelib..mpe_security;
  where &dc_dttmtfmt.lt tx_to and ACCESS_LEVEL='VIEW';
run;

/* check for any matching groups */
proc sql noprint;
create table matches as
  select * from sec
  where upcase(sas_group) in (select upcase(groupname) from groups);
select count(*) into: securitygroupscount from matches;
select count(*) into: ALL_CNT from matches where libref='*ALL*';
%put securitygroupscount=&securitygroupscount;
%put ALL_CNT=&ALL_CNT;
%mp_abort(iftrue= (&syscc ne 0)
  ,mac=&_program..sas
  ,msg=%str(syscc=&syscc)
)

%macro mpestp_viewlibs();
%if not %symexist(DC_RESTRICT_VIEWER) %then %let DC_RESTRICT_VIEWER=NO;

/* scenario 1 - user is in admin group, hence can view all libraries */
proc sql noprint;
select count(*) into: scenario1 from groups where groupname="&mpeadmins";
%if &scenario1>0 %then %do;
  %put user in admin group (scenario1=&scenario1);
  %return;
%end;
/* scenario 2 - viewer unrestricted and no groups listed */
%if &DC_RESTRICT_VIEWER=NO and &securitygroupscount=0 %then %do;
  %put DC_RESTRICT_VIEWER=&DC_RESTRICT_VIEWER;
  %put securitygroupscount=&securitygroupscount;
  %return;
%end;

/* scenario 3 - an *ALL* libref is listed */
%if &all_cnt>0 %then %do;
  %put all_cnt=&all_cnt;
  %return;
%end;

/* scenario 4 - specific librefs listed */
%if &securitygroupscount>0 %then %do;
  %put scenario 4;
  %put securitygroupscount=&securitygroupscount;
  proc sql;
  delete from mm_getLibs
    where upcase(libraryref) not in (select upcase(libref) from matches);
  %return;
%end;

/* viewer restricted and no groups listed */
%if &DC_RESTRICT_VIEWER=YES and &securitygroupscount=0 %then %do;
  %put DC_RESTRICT_VIEWER=&DC_RESTRICT_VIEWER;
  %put securitygroupscount=&securitygroupscount;
  data mm_getlibs;
    set mm_getlibs;
    stop;
  run;
  %return;
%end;

%mp_abort(iftrue= (1=1)
  ,mac=&_program..sas
  ,msg=%str(unhandled security logic err!)
)

%mend mpestp_viewlibs;
%mpestp_viewlibs()

%global dc_viewlib_check;

/**
* deal with invalid and duplicate library definitions
*/
proc sort data=mm_getlibs;
  by libraryref libraryname;
run;

data mm_getlibs;
  set mm_getlibs;
  by libraryref;
  if symget('dc_viewlib_check')='YES' then do;
    /* note - invalid libraries can result in exception errors. If this happens,
      configure the dc_viewlib_check variable to NO in Data Controller Settings
    */
    rc=libname(libraryref,,'meta',cats('library="',libraryname,'";'));
    drop rc;
    if rc ne 0 then do;
      putlog "NOTE:  Library " libraryname " does not exist!!";
      putlog (_all_) (=);
      delete;
    end;
  end;
  if not first.libraryref then delete;
run;

proc sort data=mm_getlibs out=saslibs;
  by libraryname;
run;

%mp_abort(iftrue= (&syscc ne 0)
  ,mac=&_program..sas
  ,msg=%str(syscc=&syscc)
)

%webout(OPEN)
%webout(OBJ,saslibs,missing=STRING)
%webout(CLOSE)

%mpeterm()
