Tuesday, January 7, 2014

Simple scripting in Common Lisp

I know enough Bash to read simple scripts, but I am always having a hard time when I am trying to write a script that does something that is more complicated than a one-liner that substitutes arguments into a template. I can eventually figure things out, but I have never bothered to develop my Bash skills, programming in it for me is error-prone and time-consuming.

So recently I have started experimenting with scripting in Common Lisp. It turns out to be very, very easy and convenient if you already know CL. I usually start scripting with a skeleton that looks like this:

(cl:defpackage #:script
  (:use #:cl)
  (:export #:run))

(cl:in-package :script)

;;; code comes here

I run things from SLIME and experiment with the REPL. When I think that I am approaching a solution, I write the main function run:

(defun run ()
  ...)

Then I use the following Makefile to compile it with cl-launch:

myscript: myscript.lisp
        cl-launch --lisp sbcl --file myscript.lisp --dump '!'   \
        --output myscript -i '(script:run)'

You can of course also include ASDF libraries, check the help of cl-launch.

For interfacing with the environment (pathnames, files, OS, etc), I find the UIOP compatibility library really helpful. It is included with ASDF, so most likely it is already on your computer.

4 comments:

  1. Thanks for your appreciation of UIOP. Have you tried inferior-shell? It provides a nice front-end to uiop:run-program.

    ReplyDelete
    Replies
    1. Yes, I am using inferior-shell and I find it very nice. Thanks for all those great libraries!

      Delete
  2. Also, you may or may not like asdf's program-op.

    ReplyDelete
  3. It would be nice to have a bit fuller post showing how to do various things one commonly does in bash and other shells such as pipes, IO routing, environment variable interaction, and so on. As it is this seems like merely a hint that it can be done and pointing to a possibly useful piece of doing it.

    ReplyDelete