- Notifications
You must be signed in to change notification settings - Fork54
A fertile ground for Clojure tooling
License
clojure-emacs/orchard
Folders and files
Name | Name | Last commit message | Last commit date | |
---|---|---|---|---|
Repository files navigation
A Clojure library designed to provide common functionality for Clojuredevelopment tools (e.g. Clojure editor plugins and IDEs).
Right noworchard
provides functionality like:
- enhanced apropos
- classpath utils (alternative for
java.classpath
) - valueinspector
- Java class handling utilities
- Utilities for dealing with metadata
- Namespace utilities
- Fetching ClojureDocs documentation
- Finding function dependencies (other functions invoked by a function) and usages
Much of the tooling code required to build Clojure editors and smart REPLsis tool-agnostic andshould be reused between tools, instead of copiedand altered in each and every tool.
Having a common tooling foundation typically means:
- Better foundation (e.g. more functionality, good documentation, etc) with more contributors
- Less work for tool authors as they don't have to reinvent the wheel for every tool
- Happier end users
Orchard is meant to be used to build programmer tooling relying on inspecting the state of a running REPL.REPL-powered tooling has been a core Lisp idea for many years and there are many Clojure librariesin that space (e.g.compliment
,tools.trace
,sayid
, etc).
One thing to keep in mind is that Orchard relies (mostly) on runtime information, not the source code itself.In simple terms - only code that's loaded (evaluated) will be taken under consideration. That's pretty differentfrom the static analysis approach taken by tools for most programming languages where it's not possible toeasily inspect the state of running program.
Some other design goals are listed bellow.
Orchard is meant to run alongside your application and we can't have adev tools library interfere with your app right? Dependency collisions are nasty problems which are best solvedby making sure there can't be any shared libraries to cause the conflict.
Code editors can't know what symbols resolve to without consulting a REPL that's why they would typicallysend a combination of a symbol name and some ns (e.g. the current namespace), so they can be resolved tosome var on which an operation would be invoked.
That's why the majority of the functions in Orchard take a combination of a ns and a symbol instead of a var.Probably down the road we'll provide var-friendly versions of most functions as well.
No matter whether you're using nREPL, a socket REPL, or prepl, Orchard has your back. nREPL clients mightopt to wrap some of the Orchard functionality in middleware for convenience (ascider-nrepl
does), but theycan just eval away if they please.
Documentation for the master branch as well as tagged releases are availablehere.
orchard requires Clojure 1.10+ and Java 8+.
Note
Java 8 is soft-deprecated in Orchard since version 0.29. Core Orchard funcitonality continues to work on JDK 8, but these following features don't:
- Java sources parsing
Just addorchard
as a dependency and start hacking.
[cider/orchard"0.31.1"]
Consult theAPI documentation to get a better idea about thefunctionality that's provided.
Orchard interacts with Java source files (.java
files) in several ways:
- Locates the Java source files to enable the "jump to definition" functionality.
- Also enables "jump to file:line" from the printed stacktrace (a CIDER feature).
- Parses Java sources to extract additional information about Java interoptargets (constructors, methods).
- Allows jumping directly to method definition in the Java source file.
- Extends the documentation for interop targets with Javadoc comments, exactmethod argument names.
Currently, Orchard is able to find Java source files in the following places:
- On the classpath.
- In the
src.zip
archive that comes together with most JDK distributions. - For clases that come from Maven-downloaded dependencies — in the special
-sources.jar
artifact that resides next to the main artifact in the~/.m2
directory. The sources artifact has to be downloaded ahead of time.
Orchard providesorchard.java.source-files/download-sources-jar-for-coordinates
function todownload the sources by invoking a subprocess with one of the supported buildtools (Clojure CLI or Leiningen). You can call this function at any point oftime on your own. Alternatively, you can bind the dynamic variableorchard.java.source-files/*download-sources-jar-fn*
to a function whichaccepts a Class object, and Orchard will call this function automatically whenit fails to locate a Java source file for the class. Usage example:
(binding [src-files/*download-sources-jar-fn* #(src-files/download-sources-jar-for-coordinates (src-files/infer-maven-coordinates-for-class %))] (class->source-file-url <class-arg>))
If the source file can be located, this is usually enough for basic "jump tosource" functionality. For a more precise "jump to definition" and forJavadoc-based documentation, Orcard will attempt to parse the source file.
Having JDK sources archive ($JAVA_HOME/lib/src.zip
) is important fordevelopment of Java-related features in Orchard. Certain features parse thoseJava sources as a source of information. The archive doesn't need to be on theclasspath, it just need to exist in the distribution.
You can install Orchard locally like this:
PROJECT_VERSION=99.99 make install
For releasing toClojars:
git tag -a vX.Y.Z -m "Release X.Y.Z"git push --tagsgit push
To run the CI tasks locally use:
maketest cljfmt kondo eastwood
These functions use a Clojure compiler implementation detail to find references to other function var dependencies.
You can find a more in-depth explanation in thispost.
The important implications from this are:
- very fast
- functions marked with meta
:inline
will not be found (inc
,+
, ...) - redefining function vars that include lambdas will still return the dependencies of the old plus the new ones(explanation)
- does not work on AoT compiled functions
As noted earlier Java 8 is soft-deprecated in Orchard since version 0.29. Core Orchard funcitonality continues to work on JDK 8, but the following features don't:
- Java sources parsing
We are aware that some people are stuck using Java 8 and we'll keep supporting for as long as we can, but it's no longer a priority for us that every feature works with Java 8.
OriginallySLIME was the mostpopular way to program in Clojure with Emacs and a lot of usefulfunctionality was created for it to support things like codecompletion, value inspection, finding references, apropos and soon. This functionality was implemented as a swank adapter written inClojure and lived in theswank-clojure project.
SubsequentlyCIDER andcider-nrepl replacedSLIME and swank, and much code was moved fromswank-clojure
tocider-nrepl
and continued to evolve there.
You can watch the presentationThe Evolution of the Emacs tooling forClojureto learn more about all of this.
This project is an effort to prevent repeating the mistakes of thepast -cider-nrepl
was split into two libraries, so that non-nREPLclients can make of use of the general functionality contained incider-nrepl
(e.g. things likeapropos
,inspect
, etc).
Copyright © 2018-2025 Bozhidar Batsov & contributors
Distributed under the Eclipse Public License either version 1.0 or (atyour option) any later version.
About
A fertile ground for Clojure tooling