Welcome, everyone, to this Emacs Conf 2021.
My name is Fermin. I work as
a Common Lisp engineer at RavenPack,
and today I'm going to talk about
CLEDE: the Common Lisp Emacs Development Environment.
So what is CLEDE?
So CLEDE is a project
I've been working on this year
for better... well, yeah...
a better Common Lisp integration
for static tools and
for static and integrated Emacs tools.
And to understand better what
CLEDE is, one first has to understand
the base that I use...
so the foundation that I use for CLEDE.
Um, so it is CEDET--
and specifically Semantic--
so we first have to talk about and
understand what it is.
So CEDET is a collection
of Emacs development environment tools.
It was created by Eric Ludlam
(I hope to say that name right)
in the late 90s, and
the idea was to create entire IDE for Emacs.
CEDET is still integrated into Emacs,
and it has a lot of interesting things
that are not used for too many people,
so I'm going to explain some of those.
First, let's go with the good ones that
one that I use for CLEDE and that can
be used for other projects as well.
Some of the features that
CEDET has is parse generators
so we have Wisent and Bovine.
Wisent is basically a Bison clone
that was written in Emacs Lisp
that you can also specify grammars.
It's a really big and rather complex
tool to work with,
and it's secretly used for, as far as
I know, two languages.
They're not also well supported,
but we'll get into that later.
Also Bovine, which is a way more
simple tool, like you can...
you don't need grammar files,
you can write just in plain Emacs Lisp.
And you also have utilities to work with
those generated tag trees, so to say.
These are not AST parsers like real Bison;
they are tag-based so they basically get
tags and extract information from them,
and I can use that information
with Emacs Lisp
to contextually understand better
the language that you're parsing,
but in general,
this decision was made (as far as I know)
because of the Emacs Lisp
limitation of the time.
So Emacs was a rather
slower Lisp-- slow Lisp--
so they decide to just use
tag-based thing instead of a parse--
I mean-- an AST-based one.
And Semantic give you some utility with
that as Senator, for example, give you
some semantic navigation.
So CEDET is way more than this,
but this is not a CEDET talk.
So if you want to get more information,
you can go to the official webpage.
I have to say that it is outdated, and
Emacs changed some things over the years
because CEDET was merged into Emacs
in 2011, as far as I know.
You can also go to the official Emacs
documentation (the manual), which will get
more information about every tool,
but it's a really interesting thing, and
I'm really sad that it is forgotten.
So let's go with the bad things:
that CEDET is an abandoned project.
This has some benefits like it's not
going to change that much,
but it's, of course, not ideal.
Most of the tooling that CEDET
have right now are surpassed
by other packages.
And at first, I know Eric was working
with C at the time so he totally has
"real support" so you can use CEDET
for other languages, but
to work really like an IDE, more or less,
it's all the...
C is the only language supported,
and maybe some simple C++, but that's it.
It needs more documentation.
People really don't know how to use it
because, I have to say, rather complex
to get a project working with it,
and then make use of Semantic
because [it] needs some maintenance and
to update the code.
But I will argue that even with these
deficiencies, it's usable, and
I use the foundation of base for
parse infrastructure for other languages.
I will say that with Common Lisp was
rather easy because
CEDET already have Emacs Lisp parser
even though it's not great.
It's easy to adapt and to use.
It's not used in an Emacs
right now because, well,
Emacs know very well itself,
but it's there.
So these, of course, are static parsers
so you don't need to run any
other language-specific tools, which is
an advantage for some things.
And this was basically CEDET is,
and I use the parse infrastructure
and some tools
to create a parser for Common Lisp.
Well, more or less. *laughs*
Let's go to details.
So I will say that it's not a parser
by itself because, as we all know,
to parse a macro-based language
is really hard.
Mostly if you cannot have contextual
information because if you create code
at compile time or runtime is really hard
if you don't have run time, right?
Basically, CLEDE can be described
as a Semantic extension.
So basically it's like,
you can have Semantic
and use it with Common Lisp code
and some Common Lisp Emacs tools.
So Bison (which is not Bison) is
Bovine, and Semantic and Senator
for navigating tags,
and then communication with SLIME, SLY,
and inferior Lisp.
That means... I will show that later, but
basically, you can parse the buffer,
get some tags,
get information about the tags that you want,
and then send some of that information
to the SLIME, SLY, or inferior Lisp REPL buffer,
so you can get both things
at the same time.
And given that it's a Lisp language,
this can be pretty interesting.
Also I wrote some common package integration,
so even though there's not
a Common Lisp standard,
there's some libraries that are used
by basically everyone.
They're not part of the standard,
but yeah.
A lot of people use it: like `asdf`,
which is the package manager,
I will say it's [`asdf` is] the
definition packages, so to say,
better than packages itself
and have more features.
I wrote a nice integration with it
and also `fiveam`,
which is a well-known test package.
I just wrote this as an example
on how we can do with CLEDE.
Let's look at the features,
and then we go to a demo.
You can go to the repository.
Currently, it's not in Melpa
although I wanted
to merge it-- I mean, to add it--
to Melpa in the future.
I want to clean the code and
add some more features;
I'm working on that and now
like an eagle, so to say...
but yeah, you can go here and then check
all the features and test it.
To install is pretty easy:
just "add to path" thing.
You don't need any external dependencies;
everything's in Emacs.
This was tested with Emacs 27,
but probably going to work
with Emacs 25 onwards so
it shouldn't be any problem.
So let's go with the features.
This is some CEDET integrations,
and first, like I said, it has
support for SLY, SLIME, and inferior Lisp.
If you are Common Lisp developer, you
probably know a SLIME and a SLY,
and inferior Lisp is basically
just stock Emacs REPL.
I support all three equally, so to say,
and we have also `fiveam` integration,
the ability to-- as I'm going to show later,
you have the ability to send a test--
either packages or an entire suite of tests,
and `asdf`, which currently I'm just
supporting basic project navigation
and some information,
but it's a work-in-progress.
I also have some general activities
that are not directly related to CEDET
but part of the CLEDE package, which
is CLEDE highlight.
It's highly inspired by the
Emacs re-factor `erefactor`.
Basically, you have some nice
highlights for lint variables.
I want to expand that to also
support parameters and function stuff,
but it's not a high priority for me.
But yeah, I sometimes use this;
it's pretty neat when you have a big lint.
Also some refactoring utilities...
some of those can be said
that it's overlapped with some...
because it is a string base, it doesn't
have too much context information,
but yeah, some sort of
`replace-symbol-in-region` and `symbol-tag`.
And then some CLEDE commands.
This is the thing that I use all the time.
It's like you're going to find
some commands to send to a REPL.
I will show some example, but basically,
you have already an example.
You define a list of commands,
you put name, and then you put the
Common Lisp code that you want to send.
Given that, you're writing this
Emacs Lisp in your configuration.
You can have some runtime information
when the code is sent, right?
so insert, get a variable value, or whatever.
OK, `imenu` integration.
Yes, Semantic...
CEDET has a great `imenu` utilities
to have a better `imenu`.
`imenu-list` also works really well.
So you have better... when you go to a file
that you don't fully know what is inside,
it's better to navigate having like a tree.
Yeah, this one's the thing is going
to show that Senator, which is
Semantic navigator, and then some
Semantic-specific tools like `complete-jump`,
which I don't use this one too much
because we have SLY/SLIME,
but they're there, so yeah.
Like I said, Common Lisp library support,
which is duplicated.
OK, so let's go to the demo.
Um.
Let's go to the demo file.
Right.
First, we have to do is enable CLEDE.
This is pretty easy:
we call `clede-start`, right,
and now it's started.
CLEDE is not an asynchronous parser so
Semantic (in this case, Bovine) is not.
If the file is large, it may take some time.
It shouldn't because we have
powerful computers, but if your
computer is not that powerful,
it may take a while.
To see the information that has been
parsed, we're going to call `bovinate`.
Oops... oops...
Oh! I have to-- sorry...
Let's enable Semantic again.
Let's start... `bovinate`...
OK, so...
This is the information that
currently CLEDE is taking from the buffer.
So we can see it's taking this, and
it doesn't know what it is,
so this is the tag name...
this is the type,
and these are some information
and the location.
OK, so we know that this is a variable,
and it has the full value.
You know this is a package, right,
because it's defined as a package.
It doesn't understand what this is.
This node is a function
because of the `fun`,
and some of this is code,
and it also understands some tests
because it has `fiveam` integration.
If it detects that has some test here
it will know that, indeed, it is test.
So let's try some, first, `imenu`.
So we can see here we have...
I understand that this have
some sort of `fiveam` switch
and some tests defined.
It understands this package, and
it'll give you some variables-- `defuns`,
and it also will give you some misc
for things that doesn't know what it is.
And you can also
navigate with this-- like this `imenu`.
So, um, let's go first with some Senator.
So with Senator, we can navigate,
go to the next stack, previous stack,
all this, um, top-level `s-expression`
are basically a tag, even though
it's code... you can navigate, right.
Um, copy/kill this or some other stuff.
Um, some interesting thing that we can
do is let's launch SLY, right.
Um, let's load `fiveam`,
and let's send some tests.
We can say, OK, `clede-fiveam-send-current-test`,
and it will-- OK, have to compile
this file first.
OK, you don't like this...
you compile the tests.
OK... um... well...
I don't have-- yeah, I don't have
the switch here so let's...
OK, yeah because I guess it's getting...
sorry about this...
Let's say we're going to send this test...
It isn't working...
OK, why are you not working...
maybe because we have to go
to the package `fiveam`.
Yes, sorry... um...
Yeah, so we're gonna go here, and
we can say `fiveam-send-tests`,
and there we have it.
It will send the test
that we are currently in, right.
So that's the thing.
Another interesting thing that I said is
`clede-highlight-minor-mode`.
Basically, work in `let`'s context
to know where to highlight
all the variables,
and we can disable.
What else do we have?
So we have framework integration.
You can go `clede-` and
see what more commands are.
`commands-run` are basically a way
to define commands, you have a variable,
which is `clede-commands-list`.
Let's explain that you can get
some system working
or whatever command you want, right.
Also you have `asdf` basic integration.
You can go to a definition file
of some of the systems are already loaded.
For example, let's go to here,
and we go to the definition file--
there's the file, right?
This is used because I'm sending
commands for the REPL, so this
functionality is not provided
by CEDET or Semantic,
but I can also get some sort
of information for `asd` file,
which is a work-in-progress,
but you can go to some component file
when you have a big `asd` file
with lots of components
and some other interesting thing.
Like I said, that's a work-in-progress,
Yes, so this is most of the functionality.
The most interesting thing, I think,
is the base for the foundation.
So you can expand: let's go to source code,
for example, that `fiveam`.
So as we can see here, this is
the `fiveam` integration, and to add it,
I just define some new functions,
and then you use this...
set up a new form parser that we use
to get some information
about the `s-expression` top-level,
and we define the names,
we define information we want to take
from the symbol and everything else.
Also some [??] types
that would be going to be added
to the `imenu` thing:
for example, `imenu test switch and test`.
And then, these are, for example,
some function to send information
to the SLY, SLIME, or inferior Lisp
depending on the Lisp that you're using.
So I do not have more time.
Sorry about that.
Thank you very much.
My name is Fermin.
You can send me a mail in my mail,
and that's my webpage.
I hope you like it.