i just applied a patch which adds "repl commands" to slime.
the syntax is #, command-name &rest args. I used the comma instead of #: since, afaict, #, will never appear at the start of a valid lisp form (unless you're messing with the read table in which case you can just deal with it).
the following commands have been implemented:
cd namestring - change *default-pathname-defaults*
pwd - return the namestring of *default-pathname-defaults*
sayoonara - quits the lisp and kills all slime related buffers (this has a weild bug whereby the next connection attempt after a sayoonara will fail).
cload file &optional force - loads file. if the source is newer than the compiled, or the compilied doesn't exist, or force is T then the file is compilied before being loaded.
pack &optional new-package - sets or returns the current package. the utility of this is debatable.
+ - resend the top of slime-repl-input-history, don't change slime-repl-input-history.
I have tried to make defining commands easy, see the bottom of swank.lisp for the defs of the current commands. I may very well have broken the repl, comments welcome. These should probably be re-organived into an explicit elisp side stuff and lisp side stuff. we'll see if future commands need it enough to do that.
-- Marco Ring the bells that still can ring. Forget the perfect offering. There is a crack in everything. That's how the light gets in. -Leonard Cohen
Marco Baringer mb@bese.it writes:
i just applied a patch which adds "repl commands" to slime.
I like it a lot!
"Marco" == Marco Baringer mb@bese.it writes:
Marco> i just applied a patch which adds "repl commands" to slime. Marco> the syntax is #, command-name &rest args. I used the comma instead of Marco> #: since, afaict, #, will never appear at the start of a valid lisp Marco> form (unless you're messing with the read table in which case you can Marco> just deal with it).
A few comments (but do not misunderstand, I think the idea is good).
I am not sure that I am all that enthusiastic about the choice of #, rather than #: since there are already at least 3 systems using the latter.
I am also not quite sure why you need something that cannot start a lisp form. Couldn't you just check to see if <whatever> was a defined command and if not just put <whatever> back into the stream?
It may be nice to have a command that manipulates *default-pathname-defaults* but I think that calling it `cd' will confuse at least CMUCL users (for instance, `load' does not takes its notion of CWD from *default-pathname-defaults*).
An important feature of a REPL command facility is a help command that gives an overview over what commands are currently available and is able to provide a simple synopsis of their arguments.
It is unfortunate that any mistakes with a command lands you in the break loop. At least I tend to make lots of mistakes and having to exit the break loop each seems rather annoying (to me at least).
One of the great advantages of the REPL commands of ACL and the look-alike packages is that you do not need all that extra quoting. Ie. it would be nice to extend the repl reading such that one could do
,cd ..
rather than having to write
,cd ".."
PS
I know I sort of promised to look into integrating one of the REPL packages into SLIME. I will make an effort to get back to that, RSN.
------------------------+----------------------------------------------------- Christian Lynbech | christian #@ defun #. dk ------------------------+----------------------------------------------------- Hit the philistines three times over the head with the Elisp reference manual. - petonic@hal.com (Michael A. Petonic)
Christian Lynbech christian.lynbech@ericsson.com writes:
"Marco" == Marco Baringer mb@bese.it writes:
Marco> i just applied a patch which adds "repl commands" to slime. Marco> the syntax is #, command-name &rest args. I used the comma instead of Marco> #: since, afaict, #, will never appear at the start of a valid lisp Marco> form (unless you're messing with the read table in which case you can Marco> just deal with it).
A few comments (but do not misunderstand, I think the idea is good).
I am not sure that I am all that enthusiastic about the choice of #, rather than #: since there are already at least 3 systems using the latter.
This could perhaps be made configurable. I like comma much better.
It may be nice to have a command that manipulates *default-pathname-defaults* but I think that calling it `cd' will confuse at least CMUCL users (for instance, `load' does not takes its notion of CWD from *default-pathname-defaults*).
True, this should be done via backend functions. We already have one for setting the default directory (which sets (ext:default-directory) in CMUCL), we just need a new one for reading it.
I agree with your other suggestions, there's lots of nice stuff we can do with this feature in the future.
-Luke
Luke Gorrie luke@bluetail.com writes:
Christian Lynbech christian.lynbech@ericsson.com writes:
It may be nice to have a command that manipulates *default-pathname-defaults* but I think that calling it `cd' will confuse at least CMUCL users (for instance, `load' does not takes its notion of CWD from *default-pathname-defaults*).
True, this should be done via backend functions. We already have one for setting the default directory (which sets (ext:default-directory) in CMUCL), we just need a new one for reading it.
Doesn't the function for setting it keep *default-pathname-defaults* in sync with whatever other notion the Lisp may have of the cwd? If not, it probably should. And thus the read-cwd function can simply return *d-p-d*. (Though we might want functions to resync the Lisp's other notion cwd with *d-p-d* or vis versa in case they get out of whack.)
-Peter
Peter Seibel peter@javamonkey.com writes:
Doesn't the function for setting it keep *default-pathname-defaults* in sync with whatever other notion the Lisp may have of the cwd? If not, it probably should. And thus the read-cwd function can simply return *d-p-d*.
Yes. Upon actually reading it, this is exactly how Marco's code works.
-Luke
since the slime repl is built into emacs i'm wondering if we need to stick to the "type a magic command into the repl buffer" idea current embodied by the various repls.
here's a completely different way of doing it:
When you are at the start of the repl there is a special character (by default #,) which begins a repl command. if you type this charcter we ask you (via a completing read in the mini-buffer) what command you want to run, based on what you type we pass control off to a regular interactive emacs function which gets its parameters via the minibuffer (or whatever) and executes whatever code it wants.
Pros:
1) we can use read-directory-name to read the arg for cd, we can using a completing read for the pack command, etc. basically we can use whatever emacs input conveniences we see fit instead of having to parse everything from the command line, and emacs is good at this stuff.
2) the repl commands are available as regular emacs functions and can be put into menus.
3) it's a hell of a lot simpler to implement.
4) we can give commands long names, completion will take care of the rest.
Cons:
1) its really different from the "obvious" definition of a repl command.
2) it doesn't show up in the repl history or buffer anymore (though this could be changed into something similar to CLIM's Listener).
3) Aborting a command mid way requires a C-g and blinks emacs, instead of just being a C-a C-k.
Given how trivial this is to implement i could just do it and we could try it out and see if it works or not.
comments?
-- Marco Ring the bells that still can ring. Forget the perfect offering. There is a crack in everything. That's how the light gets in. -Leonard Cohen
Marco Baringer mb@bese.it writes:
[...] When you are at the start of the repl there is a special character (by default #,) which begins a repl command.
If you haven't used it, allout.el has something similar for outline navigation -- when you're on a topic marker, you can navigate with the keys 'f', 'b', etc.
- its really different from the "obvious" definition of a repl command.
Slime already ain't yo mama's REPL -- it might as well take full advantage of having an Emacs around.
- it doesn't show up in the repl history or buffer anymore (though this could be changed into something similar to CLIM's Listener).
But we could give it an Emacs history ring.
Given how trivial this is to implement i could just do it and we could try it out and see if it works or not.
comments?
I have to admit, my first response on reading about using REPL commands with "," was "what's wrong with \M-x?", so I think this is an unmitigated good.
/s
"Sean O'Rourke" seano@cs.ucsd.edu writes:
Marco Baringer mb@bese.it writes:
[...] When you are at the start of the repl there is a special character (by default #,) which begins a repl command.
If you haven't used it, allout.el has something similar for outline navigation -- when you're on a topic marker, you can navigate with the keys 'f', 'b', etc.
- its really different from the "obvious" definition of a repl command.
Slime already ain't yo mama's REPL -- it might as well take full advantage of having an Emacs around.
- it doesn't show up in the repl history or buffer anymore (though this could be changed into something similar to CLIM's Listener).
But we could give it an Emacs history ring.
Given how trivial this is to implement i could just do it and we could try it out and see if it works or not.
comments?
I have to admit, my first response on reading about using REPL commands with "," was "what's wrong with \M-x?", so I think this is an unmitigated good.
I agree. Perhaps immediate keybindings for some of the most common commands and M-x for the rest and I'll be quite happy.
-Peter
We use slime-repl-command-dispatch-char to start a repl shortcut, there is a table mapping command names to elisp functions, some of these are already existing slime functions (slime-repl-set-package and slime-set-default-directory), some of these call new (very short) functions.
current shortcut set:
cd - change directory directory-push directory-pop cp - change package package-push pakcage-pop ! - defparameter + - reeval last form sayoonara - quit and close buffers
there is the seed of the idea of a help system, but nothing usefull for now.
having used it very briefly i think i like it better than the current repl commands, but i'm not applying it until there's some feedback.
-- Marco Ring the bells that still can ring. Forget the perfect offering. There is a crack in everything. That's how the light gets in. -Leonard Cohen
ok, here's version two of the repl shortcuts.
we now have a declarative macro for specifying what the shortcuts are and some help text (and we even have a help command which dispalys it! omg!). the shortcut commands get automatically defined as interactive elisp functions (unless the shortcut just calls an already existing function).
as before here's the patch against the latest CVS, i'll going to wait for a "damn that's cool" or a "dude, the absinthe is getting to you!" before deciding to commit or not.
-- Marco Ring the bells that still can ring. Forget the perfect offering. There is a crack in everything. That's how the light gets in. -Leonard Cohen
Marco Baringer mb@bese.it writes:
as before here's the patch against the latest CVS, i'll going to wait for a "damn that's cool" or a "dude, the absinthe is getting to you!" before deciding to commit or not.
Damn that's cool!
Luke Gorrie luke@bluetail.com writes:
Peter Seibel peter@javamonkey.com writes:
Doesn't the function for setting it keep *default-pathname-defaults* in sync with whatever other notion the Lisp may have of the cwd? If not, it probably should. And thus the read-cwd function can simply return *d-p-d*.
Yes. Upon actually reading it, this is exactly how Marco's code works.
Cool. So I just committed a change to swank-allegro.lisp that provides an Allegro specific version of SET-DEFAULT-DIRECTORY that also uses EXCL:CHDIR to keep things in sync.
-Peter