quickhack for common lisp

coming from rust and javascript, i often want to dig into the internals of the libraries im using to develop my application. usually the goal is to tweak some behavior, add an extra configuration option, add breakpoints or logpoints, or get a fuller picture of whats going on under the hood. with javascript, those tasks are easily accomplished by peeking into node_modules/. in that folder are the build outputs (the literal javascript) that my application is loading and running. with rust, it's more or less the same game, but you have to manually clear the binary cache with cargo clean -p crate and modify the source within the crates.io index. this also means you modify it for other dependencies, but when hacking on something temporarily, that's not the end of the world.

what does that look like for common lisp? coming from the typical editor and terminal tab switch workflow, things like a sophisticated repl are somewhat difficult to reach for when in a flow state. i know you can easily evaluate (in-package :external-package) and (re-)define things there, but you miss out on having the context of the source by your side (local tools, jump to definition, etc). i think a slightly less daunting approach follows, which i've dropped into my ~/.sbclrc which is loaded for every interactive lisp session:

(defpackage haze
  (:use :cl)
  (:export #:ql-hack-on))
(in-package :haze)

(defun ql-hack-on (identifier)
  "Copy the 'ql:quickloaded' result of IDENTIFIER to '(FIRST QL:*LOCAL-PROJECT-DIRECTORIES*)' for easy modifications."
  (let* ((release (ql-dist:find-release identifier))
         (archive (ql-dist:ensure-local-archive-file release))
         (local-projects (first ql:*local-project-directories*)))
    (ql-util:with-temporary-file (tar "hackable-release-install.tar")
      (ql-gunzipper:gunzip archive tar)
      (ql-minitar:unpack-tarball tar :directory local-projects)
      (let ((output (merge-pathnames (pathname-name archive) local-projects)))
        output))))

(in-package :cl-user)

what this does is define a package haze that has one exported function, ql-hack-on. in an interactive lisp session, if i want to "hack on" a package such as filesystem-utils (to say prototype hardlink support) i can evaluate (haze:ql-hack-on "filesystem-utils") and have the latest release from the preferred quicklisp distribution is placed within one of ql:*local-project-directories*, which happens to be $HOME/quicklisp/local-projects.

from there, subsequent loads ((ql:quickload "filesystem-utils")) of filesystem-utils will read from my local copy, and i can hack away. this is great for quickly prototyping additions and im glad i can find a familiar workflow with a new language. i am also interesting in how other tenured lisp programmers go by modifying quicklisp libraries, so please comment on your preferred link aggregator!

this is entry 1/52 in my quest to write one piece per week of 2025.

Emacs 30.0.93 (Org mode 9.7.11)