How to organise, test, document and package a Clojure project - clojure

I've been learning some Clojure, and I currently have a single .clj file which I edit in a text editor and which I execute on the command line.
Where can I find a guide on the practical aspects of scaling this up to larger programs/libraries?
How should I lay out multiple .clj files on the filesystem?
How should I organize and execute test code?
How should I document the program/library?
How should I package it?
I'm looking for information on the practical aspects on scaling up from small scripts to something real.

I recommend using leiningen. Running
$ lein new myproject
will create a new folder called myproject inside your current working directory with a default skeleton structure.
Inside the newly generatedmyproject folder you'll find (among others) a folder named src for clojure source code and a folder named test for your tests (leiningen will generate a default failing test).
Leiningen will let you run your tests with lein test.
You can package your project as a jar file with lein jar or create an uberjar (an executable jar with all required dependencies included) with lein uberjar.
For generating documentation I recommend autodoc which integrates nicely with leiningen.

If you are using Netbeans, there is a Clojure plugin which could be helpful to you.
Creating a Clojure project with it creates a bunch of folders: Source Packages, which contains a default package called com.yourcompany, Test Packages, Libraries, which contains the .jar for Clojure and a link to the JDK, and Test Libraries, which contains JUnit.

I use a combo of:
Intellij Idea with the La Clojure plugin
Leiningen
Clojars
Midje, for testing/mocking
Git
Good luck!

Related

How do I get cljx to compile clojure files into classes during uberjar?

I'm using cljx to build cli / cljs applications but haven't for the life of me been able to create a self packaged compiled jar.
Here's my project file -> https://gist.github.com/chrispwood/4db33e53555a8e8787d1
When I run lein jar or lein uberjar I get only a packaged jar with the clj files, not the class files. See the output file above ^^.
Does anyone know how to make sure the transpiled clj code gets compiled into class files?

Is there a better way to resolve emacs lib dependency?

I came across a problem when I tried to run the test files in a emacs project.
For example, I cloned this project into my home directory, cd into test dir and then used emacs -batch -l ert -l nrepl-tests.el -f ert-run-tests-batch-and-exit to run the tests. But it couldn't locate the file nrepl.el which was not in the same directory. So, I copy one into ~/nrep.el/test. But it said "Cannot open load file: clojure-mode". That is the question I'm concered.
I do have clojure-mode and other libs nrepl.el use. But they are all in different directory(In my case, ~/emacs.d/packs/live/clojure-pack/lib/). Do I have to duplicate these files into my cloned nrepl project in order to run the test? Is there a better way to run test files like we do in IDE. For instance, in Intellij, I simply write import statements in test files, and it automatically prepares the dependency libs for me. This bothers me quite a lot. I'm wondering if there is a best practice for this problem.
If I understand you correctly, I'm under impression that Carton is precisely what you're looking for to overcome these dependency issues: package maintainer is expected to write a small file containing package dependencies including development ones, like ert, and run emacs via carton exec which will make sure everything is downloaded to a certain directory and this directory is added to load-path.

How do I get intellij's clojure console to load the dependencies defined in leiningen?

I've installed the "la Clojure" and "leiningen" plugins. I've created a clojure project and added the lib/ folder as a library in my project. With this done the editor knows about the libraries and if I 'run' a clojure file it successfully loads the dependencies, but if I start a console within intellij it doesn't load the dependencies. How do I get the console to load them?
I open the project settings, add lib and lib/dev as JAR directories (IntelliJ scans them for changes and updates the classpath automatically). This works with the Clojure console.
I use
lein pom
to generate pom.xml if it does not already exists and let idea to use maven to track the dependencies
I created a clojure file that requires all of my source files. then from the repl screen I (load "start-repl.clj"). It's not a really good solution because of the manual steps but it gets me hacking...

How do I create an executable file in clojure?

I've been learning clojure on the REPL environment with Clojure Box.
How can I make an executable file (.jar)?
I'm wondering if something like this is possible:
write clojure code on notepad and name it project.clj
compile project.clj
get executable file
Step #2 doesn't have to be done in command line. IDE is fine.
As Erhan Bagdemir answered, you should use Leiningen. Here's how I do it on Windows:
Install Leiningen on Windows
You're going to download the Leiningen script and put it somewhere on your PATH. If you have a folder already on your path that you use for executable scripts, if not, do the following:
Download the Leiningen package from Github.
Unzip it in your home folder (e.g. /Users/vikbehal)
Add the folder that was created by unzipping to your PATH. To do this, open the Control Panel, and go to the System area where you can edit your Environment Variables. Edit either the system or your user's PATH value by adding /Users/vikbehal/lein (or whatever the folder is called) to your PATH, making sure to keep that entry separated from others by a semicolon (;).
Press Ok to save your changes.
You can verify that you've successfully installed Leiningen by opening up a command prompt and running lein help. You should see Leiningen installing some initial files. If you get an error, make sure you've properly added the folder where Leiningen lives to your PATH.
Use Leiningen to Develop
Leiningen gives you a good default directory structure, handles dependency management, and ensures that Java's classpath is set properly when running a REPL or, in this case, jarring your application.
Here's a run-down of Leiningen standard commands:
# Start a blank project
lein new my-project
# Pull down dependencies defined in your project.clj file
lein deps
# Create a "library" jar of your project
lein jar
# Create an executable jar of your project
lein uberjar
It looks like that last command is what you want, right? First, you need to configure a few things, so that Leiningen can build your executable jar properly.
Configuring for an Executable/Standalone Jar
You need to do three things to make lein uberjar work properly:
Write a -main function that will act as the "entry point" to the execution of your jar file. (Note the -, it denotes that this function is more like a "Java method" than a regular Clojure function.)
Make sure you add a (:gen-class :main true) declaration in the ns namespace declaration at the top of the file that contains your -main function.
Add a :main my.main.namespace entry in your project.clj
Now run lein uberjar. While developing, you can alternatively use lein run if you want to test how your application would behave as an executable jar, but don't want to explicitly re-jar every time you make a change.
Use Leiningen to create an uberjar.
with Leiningen:
http://www.bagdemir.com/2011/07/04/creating-new-projects-with-leiningen/
Just for variety I though I would mention the maven clojure plugin for those who want to keep to their Java roots.

Clojure deployment?

What is the easiest way to make a clojure app into an executable like http://rawr.rubyforge.org/ does for ruby? (exe and app files too)
Use leiningen and build an uberjar(standalone jar that contains all dependencies) from the project.
As Alex Ott mentions in the comment to my answer, another may to build your app is to use Maven + Clojure plugin for maven. Afterward you may use a tool such as IzPack to generate an installer or an executable wrapper for your jar artifact. You may use IzPack with leiningen as well of course - it doesn't care about the build system at all - only about the resulting files :-)
After you have the uberjar there are many option to wrap it in a native executable launcher for windows - izpack2exe, jsmooth, jar2exe, executor, etc...
To expand on Bozhidar's answer leiningen makes it super easy to generate a jar that packages your app and its dependencies. Just run lein uberjar from the terminal when you are inside your project directory and it will create a file project-name-0.1.0-standalone.jar that can be run with java -jar where "project-name" is the name of your project. You want to make sure that is your project.clj you set :main to your file that has a -main function. Also in your main file you want to put (:gen-class) inside your namespace declaration like so:
(ns project-name.main
(: require ...)
(:gen-class))