;;
;; emacs-lisp init code for Modules
;;

(setenv "MODULESHOME" "@prefix@")

(defvar Modules-history '() "module cmd history list")

(defun Modules-module (command)
  "Run the string COMMAND as a Modules cmd using the tcl version of modules.
Any resulting output is placed in buffer \" *modules-cmd*\".
This should consist of a single line, a filename, which is
expected to contain Emacs lisp code to implement the indicated
module commands.  The lisp code in this file is eval'd by Emacs
on successful completion of modulecmd.tcl.

Standard error output is placed in buffer \" *module-log*\" which will
be displayed if not empty.

Return value is t on success, nil otherwise."
  (interactive (list (read-string "Module cmd: " nil 'Modules-history)))
  (let
      ((cmd-buffer (get-buffer-create " *modules-cmd*"))
       (log-buffer (get-buffer-create " *modules-log*"))
       (log-scratch-file (make-temp-name 
                          (expand-file-name "modules-log"
                                            (if (fboundp 'temp-directory)
                                                (temp-directory)  ;; XEmacs
                                              temporary-file-directory))))
       (status nil))

    ;; clear cmd buffer, log buffer is replaced below 
    (set-buffer cmd-buffer)
    (delete-region (point-min) (point-max))

    (if (condition-case nil
            ;; call-process on Emacs cannot write stderr to a separate buffer
            ;; so it must go to a file and then get pulled into the log buffer
            ;; (XEmacs *can* direct stderr to buffer, but not worth special case)
            (progn
              (apply 'call-process "@TCLSH@" nil
                                   (list cmd-buffer log-scratch-file)
                                   nil          ;; don't display stdout
                                   "@libexecdir@/modulecmd.tcl"
                                   "lisp" (split-string command))
              t)
          (error nil))
        (progn
          ;; pull any log info from log-scratch-file into log-buffer
          (set-buffer log-buffer)
          (insert-file-contents log-scratch-file nil nil nil t)

          ;; display any output written to stderr ( eg: module help|list )
          (if (> (buffer-size) 0)
              (switch-to-buffer-other-window log-buffer))

          ;; Run any setenv, etc commands produced by modulecmd.tcl
          ;; cmd-buffer should currently contain the pathname of file to run
          ;; Note: use eval-buffer instead of load-file to avoid stomping
          ;; any (message) output from the script itself.
          (set-buffer cmd-buffer)
          (if (> (buffer-size) 0)
              (progn
                ;; run it carefully.  If an error is thrown, catch it and
                ;; propagate the fact upwards as a nil, but be sure to still
                ;; execute cleanup below
                (setq status
                      (condition-case nil
                          (progn
                            (eval-buffer)
                            t)
                        (error nil)))))))

    ;; all done, clean up
    (delete-file log-scratch-file)

    status))
