chemcop.pl

{
/* _____________________________________________________________________________________
                                                     Copyright (C) DataAspects Corp 1998
Module Name = chemcop.pl
Description= A TRIMpl program that runs on a remote Daylight Server and 
             calls various 'c' programs that use Daylight tools to 
             interact with a Thor chemical database.  Chemcop.pl is 
             called by client programs via the TRIMrpc (TRIM remote 
             procedure call) utility.  Chemcop.pl takes three parameters: 

Parameters = parm.0- action (i.e. 'db_exec': Client wants to execute remote program)
             parm.1- flag (i.e. 'load', flag to run a program that loads a 'TDT' )
             parm.2- list (list with data required by the program, i.e. a 'TDT')

Programs   = Chemcop.pl is built from blocks of code. Each block is identified
             by a flag.  When called, a block executes a remote 
             program that sends data to and from Thor, Merlin or the tool kit.  
             The chemcop.pl blocks are:

             1. 'load' executes a UNIX script 'load_cis' which takes a 
                'TDT' argument and inserts it into Thor.
             2. 'purge' executes a UNIX script 'purge_tdt' which takes a 
                'TDT' argument of a SMILES.  It keeps the SMILES, but purges
                all other data from its TDT.
             3. 'unique' executes 'unique_smile.c' which takes a 'SMILES' argument 
                and returns a USMILES.
             4. 'is_smi_in_db' executes 'is_smi_in_db.c' which takes a 'SMILES' 
                argument and returns TRUE/FALSE and error codes.
             5. 'get_chem_dat' executes 'get_data_from_cis.c' which takes a 'SMILES'
                or structure number and returns USMILES, MF, MW, CAS and ClogP.
             6. 'get_thorlist' executes 'wrno_list_from_cis' which takes a list of 
                structure numbers and returns WRNO,CAS,MW,MF,SMILES.
             7. 'minimer' executes minimer.c which takes a 'Merlin Pool Name', 
                'SMILES' and '# hits', executes a similarity search, and returns 
                a list of hits with each row containing a 'similiarity index', 
                'WRNO', and 'SMILES'.
             8. 'minimer_gen' executes 'minimer_gen.c' which takes five user defined 
                parameters ( Merlin pool name, search type, search field, search value, 
                number of hits) and returns a list with six fields (structure number, 
                search column, CAS, MW, MF, Similarity index, and SMILES).
             9. 'foreign_thor' executes 'search_foreign.c' which takes three parameters 
                ('dbname' 'datatype' 'search_value') and returns SMILES, WRNO, MF, MW,
                CAS.
            10. 'listmerlin' executes a UNIX script called listmerlin which returns 
                the names on the Merlin that are currently open.
            11. 'listthor' executes a UNIX script called listthor which returns 
                the names of the Thor databases that are currently open.
            12. 'pingchemcop' calls 'chemcop.run' to return a 'hello' message and 
                write a 'hello' message to chemcop.log on ChemServer.
            13. 'pingmerlin' executes a UNIX script called 'pingmerlin' which takes 
                the name of a Merlin pool as a parameter and returns its 'open'
                status.
            14. 'pingthor' executes a UNIX script called 'pingthor' which takes 
                the name of a Thor database as a parameter and returns its 'open'
                status.
            15. 'smi2mol'executes a C program called 'smi2mol' which takes 
                a SMILES as a parameter and returns a molfile.

Revisions:	17 June 00, added smi2mol.

...Pat McGreevy, 18 Feb 99  [McG, 18 June00]
_____________________________________________________________________________________ */

char fn[128],fn1[128],fn2[128];
int  rc;
list ll;
#define logfile "/usr2/trim/run/chemcop.log"

/*#define loging                                                     turn on logging  */
#undef loging                                                     /* turn off logging */

#ifdef logging
log(logfile,"----------");
log(logfile,to_char(SYSDATE,"DD-MON HH:MI:SS"));
if (count(parm))
  log(logfile,"parm.0= "^^parm.0);
if (count(parm) == 2)
  log(logfile,"parm.1= "^^parm.1);
if (count(parm) == 3){
  log(logfile,"parm.1: "^^parm.1);
  log(logfile,"parm.2: "^^list_curr(parm.2,0));
  }
#endif

rc= NULL;
if (parm.0 == db_exec) {                        /* client wants to execute a command  */

  if (parm.1 == "thor_load") {                  /* 'load' TDT from client into Thor   */
    fn1 = tmpnam();                             /* create filename & assign it to fn1 */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
    list_file(parm.2,fn1,"a");                  /* write TDT argument to file fn1     */
    rc = system("load_cis "^^fn1^^" "^^fn2);    /* execute load_cis.c & pass TDT arg  */
    delete(fn1);                                /* delete fn1, the TDT argument       */
    return(rc);                                 /* return error codes to client       */
    }

  if (parm.1 == "thor_purge") {                 /* 'load' TDT from client into Thor   */
    fn1 = tmpnam();                             /* create filename & assign it to fn1 */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
    list_file(parm.2,fn1,"a");                  /* write TDT argument to file fn1     */
    rc = system("purge_tdt "^^fn1^^" "^^fn2);   /* execute load_cis.c & pass TDT arg  */
    delete(fn1);                                /* delete fn1, the TDT argument       */
    return(rc);                                 /* return error codes to client       */
    }

  else if (parm.1 == "smi_unique") {            /* convert SMILES to a USMILES        */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
#ifdef logging
    log(logfile,"smi_unique:"^^list_curr(parm.2,0)^^", fn2: "^^fn2);
#endif
    rc = system("unique_smile "                 /* execute unique_smile.c             */
               ^^list_curr(parm.2,0)^^          /* pass SMILES argument from client   */
               " 1>"^^fn2^^" 2>&1");            /* return USMILES,MW,MF,CAS,ClogP     */
#ifdef logging
    log(logfile,"unique_smile returned "^^rc);
#endif
    return(rc);                                 /* return error codes to client       */
    }

  else if (parm.1 == "smi_in_thor") {           /* determine if SMILES is in Thor     */
    fn2 = tmpnam();                             /* create filename & assign it to fn1 */
    rc = system("is_smi_in_db "                 /* execute is_smi_in_db               */
               ^^list_curr(parm.2,0)^^          /* pass SMILES argument from client   */
               " 1>"^^fn2^^" 2>&1");            /* return what???????????????????     */
    return(rc);                                 /* return error codes to client       */
    }

  else if (parm.1 == "thor_getdat") {            /* get USMILES,MW,MF,CAS,ClogP        */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
                   /* parm.2 can be (smi 'c1...') or (wrno '999999') or ('cas 99-...')*/

#ifdef logging
    log(logfile,"thor_getdat tmpnam = "^^fn2);
#endif
    rc = system( "get_data_from_cis "
                ^^list_curr(parm.2,0)^^ 
                 " 1>"^^fn2^^" 2>&1");                    /* return USMILES,MW,MF,CAS */
    return(rc);                                      /* return error codes to client  */
    }

  else if (parm.1 == "thor_getlist") {          /* submit struct list; get data list  */
    fn1 = tmpnam();                             /* create filename & assign it to fn2 */
    list_file(parm.2,fn1,"a");
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
    rc = system( "wrno_list_from_cis " ^^fn1^^ 
                 " 1>"^^fn2^^" 2>&1");          /* > ascii file: WRNO,CAS,MF,MW,SMI   */
    system("echo '****' >> "^^fn2);
    system("cat missing.wrno >> "^^fn2);
    return(rc);                                             /* return code to client  */
    }


  else if (parm.1 == "minimer") {               /* Run similarity search in Merlin    */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
                   /* parm.2 can be (smi 'c1...') or (wrno '999999') or ('cas 99-...')*/
    rc = system( "minimer "
                ^^list_curr(parm.2,0)^^ 
                 " 1>"^^fn2^^" 2>&1");           /* return hit list: SIM NDX,WRNO,SMI */
    return(rc);                                      /* return error codes to client  */
    }

  else if (parm.1 == "merlin_search") {            /* Run similarity search in Merlin */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
    rc = system( "minimer_gen "
                ^^list_curr(parm.2,0)^^ 
                 " 1>"^^fn2^^" 2>&1");           /* return hit list: SIM NDX,WRNO,SMI */
    return(rc);                                      /* return error codes to client  */
    }

  else if (parm.1 == "thor_search") {           /* Run foreign search in Thor         */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
                                /* parm.2 can be "'dbname' 'datatype' 'search_value'" */
    rc = system( "search_foreign "
                ^^list_curr(parm.2,0)^^ 
                 " 1>"^^fn2^^" 2>&1");         /* return hit list: SMI WRNO MF MW CAS */
#ifdef logging
    log(logfile,"rc: "^^rc);

    while (true) {
      log(logfile,list_curr(ll,0));
      if (list_pos(ll) == list_next(ll)) break;
      }
#endif

   return(rc);                                       /* return error codes to client  */
    }

  else if (parm.1 == "merlin_open") {           /* list chem dbs loaded into Merlin   */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
    rc = system("listmerlin "^^fn2);          /* execute listmerlin sceipt,pass fname */
    return(rc);                                 /* return codes to client             */
    }

  else if (parm.1 == "thor_open") {             /* list Thor dbs that are online      */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
    rc = system("listthor "^^fn2);            /* execute listmerlin sceipt,pass fname */
    return(rc);                                 /* return error codes to client       */
    }

  else if (parm.1 == "chemcop_ping") {           /* can client can talk to chemcop?   */
    return(0);                                               /* return code to client */
    }

  else if (parm.1 == "merlin_ping") {           /* is Merlin pool open & available?   */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
                                                /* parm.2 is name of merlin pool      */
    rc = system( "pingmerlin "
                ^^list_curr(parm.2,0)^^ 
                 " 1>"^^fn2^^" 2>&1");               /* parm.2= name of merlin db     */
    return(rc);                                      /* return error codes to client  */
    }

  else if (parm.1 == "thor_ping") {             /* is Thor db open & available?       */
    fn2 = tmpnam();                             /* create filename & assign it to fn2 */
                                                /* parm.2 is name of  Thor db         */
    rc = system( "pingthor "
                ^^list_curr(parm.2,0)^^ 
                 " 1>"^^fn2^^" 2>&1");               /* parm.2= name of merlin db     */
    return(rc);                                      /* return error codes to client  */
    }

  else if (parm.1 == "smi2mol") {               /* convert SMILES to  molfile         */
      fn1 = tmpnam();
      fn2 = tmpnam();
      list_file(parm.2,fn1,"a");
      rc= system("smi2mol -s < "^^fn1^^" 1>"^^fn2^^" 2>&1");
                                     /* system returns false on success, true on fail */
      delete(fn1);
#ifdef logging
  log(logfile,"smi2mol- smi_list: "^^list_curr(parm.2,0)^^", fn2: "^^fn2^^", rc: "^^rc);
#endif
    return(rc);                                      /* return error codes to client  */
    }
  }                                                  /* end 'if (parm.0 == db_exec)'  */

else if (parm.0 == db_open) {                        /* open ascii file on ChemServer */
  if (parm.1 == "select results") {                  /* First parameter is list_open()*/
    ll = list_open("2600",1);                    /* hard code 2600 for longest SMILES */
/* this row width limits the number of rows per fetch to fetch_buffer/2600 or about 3 */
    list_mod(ll,1,1);
    ll = list_merge(ll,list_open(fn2,10000),0);
    list_mod(ll,0);
/*  delete(fn2);                                       delete fn2, file from SYS call */
    return(ll);                                     /* return data list from SYS call */
    }                                            /* end 'if parm.1= "select results...*/

  if (parm.1 == "select tdt") {                      /* First parameter is list_open()*/
    ll = list_open("/usr2/daylight/foreign_tdt.out",10000);
                         /* TDT file is fixed width @ 80 byte/rows so list_open(...)  */
                         /* No need to set width to 2600 bytes as in "select results" */
    delete(fn2);                                    /* delete fn2, file from SYS call */
    return(ll);                                     /* return data list from SYS call */
    }                                            /* end 'if parm.1= "select results...*/
  }                                              /* end 'else if (parm.0 == db_open)..*/

else if (parm.0 == db_release)  return(0);
else if (parm.0 == db_rollback) return(0);
return(1);
}