CRON jobs, TCL, and HCI all intermingling

Clovertech Forums Read Only Archives Cloverleaf Cloverleaf CRON jobs, TCL, and HCI all intermingling

  • Creator
    Topic
  • #54314
    Andy Garnes
    Participant

      I am new to CloverLeaf and I need some advice on how to tackle a problem.  I would like to write messages to a file for 12 hours at a time and then I would like move this file to a new directory and empty the old file.  I think using the UPOC protocol is the best way to go for several reasons.

      1. I need to stop the outbound thread to prevent messages from being written to the file while it is being moved, so I will need to call hci commands from a TCL script.  I think using the Upoc protocol to call the tcl script rather than using a CRON job is better since I would have to modify the profile for CRON to be able to call the hci commands with the tcl interpreter.

      2. I can leverage the

    Viewing 3 reply threads
    • Author
      Replies
      • #80965
        Charlie Bursell
        Participant

          I have done this many times.  Really no need for stopping the thread.

          Setup the OB thread as both a read and write UPoC protocol using the same proc in both places

          In the proc run mode simply write messages to the file.  In the time mode, which could be advanced scheduling or not, check to see if it is time to move the file.  If so move it if not do nothing

          There is no danger of writing to the file while moving since both the read and write cannot run at the same time

        • #80966
          Robert Milfajt
          Participant

            Just a quick idea, it would be safer, and more efficient, to move (DOS-RENAME, UNIX-mv) the file vs. copying it and clearing it.

            Robert Milfajt
            Northwestern Medicine
            Chicago, IL

          • #80967
            Rehman Masood
            Participant

              Here is something that I had written a while back. It probably does a bit more then u want (for example, it ftp’ed a file over to a server and also did some file header stuff) u can just remove that part. The thread that was writing messages to a file was called pcm_a_out. The example below checks to see the status of that thread and if it running, it will stop it, move the file away and turn it back on.

              Code:


              ######################################################################
              # Name:      ftpEpicAdtToPatientCallManager
              # Purpose:  
              # UPoC type: tps
              # Args:      tps keyedlist containing the following keys:
              #            MODE    run mode (”start”, “run”, “time” or “shutdown”)
              #            MSGID   message handle
              #            CONTEXT tps caller context
              #            ARGS    user-supplied arguments:
              #                    
              #
              # Returns:   tps disposition list:
              #            
              #
              # Notes:    
              #
              # History:   MM/DD/YYYY  Programmer  Modification
              #            ———-  ———-  ————
              #            09/27/2012  R. Masood   Initial creation

              package require ftp

              proc ftpEpicAdtToPatientCallManager { args } {
                 global HciSite HciConnName HciSiteDir
                 keylget args MODE mode                         ;# Fetch mode
                 set ctx “”   ; keylget args CONTEXT ctx        ;# Fetch tps caller context
                 set uargs {} ; keylget args ARGS uargs         ;# Fetch user-supplied args

                 set debug 0  ;                                 ;# Fetch user argument DEBUG and
                 catch {keylget uargs DEBUG debug}              ;# assume uargs is a keyed list

                 set module “ftpEpicAdtToPatientCallManager/$HciConnName/$ctx” ;# Use this before every echo/puts,
                                                                ;# it describes where the text came from

                 set dispList {}                                ;# Nothing to return

                 switch -exact — $mode {
                     start {
                         # Perform special init functions
                         # N.B.: there may or may not be a MSGID key in args
                         
                         if { $debug } {
                             puts stdout “$module: Starting in debug mode…”
                         }
                     }

                     run {
                         # ‘run’ mode always has a MSGID; fetch and process it
                         
                         keylget args MSGID mh
                         lappend dispList “CONTINUE $mh”
                     }

                     time {
                         # Timer-based processing
                         # N.B.: there may or may not be a MSGID key in args
                         puts “*** UPLOAD PROCESS STARTED ***”
                         set ftphostname “ftp.server.com”
                         set ftpusername “username”
                         set ftppassword “password”
                         set now [clock format [clock seconds] -format “%m%d%Y”]
                         if { [lsearch -exact [ls $HciSiteDir/exec] monitorShmemFile] == -1 } { exit }
                         if { [catch {set PCMmsiTocEntry [msiTocEntry “pcm_a_out”]}] } {
                             catch {msiAttach}
                             set PCMmsiTocEntry [msiTocEntry “pcm_a_out”]
                             }
                         set PCMThreadStatus [keylget PCMmsiTocEntry ALIVE]
                         set oldadtfile “/data/healthvision/cis5.8/integrator/s_his/data/pcm/pcm_a_out.txt”
                         set tmpadtfile “[file rootname $oldadtfile].${now}.tmp[file extension $oldadtfile]”
                         if { $PCMThreadStatus } {
                             puts “… stopping thread (pcm_a_out) …”
                             catch {exec hcicmd -p “epic_adt_01” -c “pcm_a_out pstop”}
                             if { [file exist $oldadtfile] } {
                                 puts “… renaming file ($oldadtfile) to a temporary location ($tmpadtfile)”
                                 file rename -force $oldadtfile $tmpadtfile
                                 }
                             puts “… starting thread (pcm_a_out)”
                             catch {exec hcicmd -p “epic_adt_01” -c “pcm_a_out pstart”}
                             } else {
                             puts “Thread (pcm_a_out) was not running …”
                             if { [file exist $oldadtfile] } {
                                 puts “… Renaming file ($oldadtfile) to a temporary location ($tmpadtfile)”
                                 file rename -force $oldadtfile $tmpadtfile
                                 }
                             }
                         if { [file exist $tmpadtfile] } {
                             set upladtfile “[file dirname $oldadtfile]/EPIC_ADT_TO_PCM_${now}.dat”
                             set hdradtfile “[file dirname $oldadtfile]/PCM_Header.dat”
                             puts “… making a copy of header file ($hdradtfile) so we can append data to it ($upladtfile)”
                             file copy -force $hdradtfile $upladtfile
                             puts “… appending data from temporary file ($tmpadtfile) to the file that will be uploaded ($upladtfile)”
                             set rfileptr [open $tmpadtfile]
                             set wfileptr [open $upladtfile a]
                             while { [gets $rfileptr line] >= 0 } {
                                 puts $wfileptr $line
                                 }
                             close $rfileptr
                             close $wfileptr
                             puts “… deleting temporary file ($tmpadtfile)”
                             file delete -force $tmpadtfile
                             if {[set conn [ftp::Open $ftphostname $ftpusername $ftppassword]] == -1} {
                                 puts “Could not connect to the ftp server ($ftphostname) … ”
                                 return
                                 }
                             puts “… uploading upload file ($upladtfile)”
                             ftp::Put $conn $upladtfile
                             ftp::Close $conn
                             set newadtfile “[file dirname $oldadtfile]/EPIC_ADT_TO_PCM_${now}.sent.dat”
                             puts “… saving upload file with new name ($newadtfile)”
                             file rename -force $upladtfile $newadtfile
                             }
                         puts “*** UPLOAD PROCESS ENDED ***”
                     }
                     
                     shutdown {
                         # Doing some clean-up work
                         
                     }
                     
                     default {
                         error “Unknown mode ‘$mode’ in $module”
                     }
                 }

                 return $dispList
              }

            • #80968
              Jeff Dinsmore
              Participant

                For situations like this, I’ve used a datestamp suffix on the file name.

                I let the TCL proc manage the file naming.

                something like:

                Code:

                set cs [clock seconds]

                set suffixHour [expr ([clock format $cs -format “%H”] / 12) * 12]

                set day [clock format $cs -format “%Y%m%d”]

                set currentFileName [format “yourFile_%s%02d00.xyz” $day $suffixHour]

                Just open the file in append mode each time and write your current message to it.

                .

                Code:

                set outFile [open [file joing /yourDir $currentFileName] a]
                puts $outFile $msg
                close $outFile

                Then, find any files in your current write directory that are NOT the current file name, and move them to the location where they’re to be picked up.

                Code:

                set fileNames [glob -nocomplain -tails -directory /yourDir *]
                foreach f $fileNames {
                 if { $f ne $currentFileName } {
                   file rename -force [file join /yourDir $f] [file join /otherDir $f]
                 }
                }

                Your time mode and/or run mode can do the file move.  The drawback to doing it in the run mode is that you’re reliant on receipt of a message to trigger it.

                I generally make an archive copy for future reference before placing it in the pickup location.

                You’d also want to ensure that from/to directories exist and may want to use catch to protect against failures – particularly with the file read/write/rename functions.

                With this approach, you don’t need to be concerned with moving a file that’s being written and, with an archive copy, you can keep track of what was sent and when it was sent.

                Jeff Dinsmore
                Chesapeake Regional Healthcare

            Viewing 3 reply threads
            • The forum ‘Cloverleaf’ is closed to new topics and replies.