This requires heinous hackery! It appears the only way to get out of clojure.main/repl is by sending an EOF character, but there doesn't seem to be a way to do that over sockets; you can only close sockets. Reading from a closed socket results in an exception, so we rebind clojure.main/skip-whitespace, which is where the reading happens, to a function that fakes an EOF if it sees an IOException. We also have to pass in a custom :caught function to suppress SocketExceptions since the clojure.main/repl will continue to attempt to perform I/O on the socket even once we are done with it.
This is Colin's plugin.clj plus a few tests.