Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Clojure: How to run my main from jar?

Tags:

clojure

I have my Clojure app packed in a jar. I am launching it as:

java -cp lib/clojure-1.2.0.jar:my-app.jar clojure.main -e "(use 'foo.main)(-main)"

Is this the only way to launch my application from this jar? Specifically, I would love to see something as simple as:

java -cp lib/clojure-1.2.0.jar:my-app.jar clojure.main foo.main
like image 542
Konrad Garus Avatar asked Dec 04 '10 16:12

Konrad Garus


3 Answers

Use

(ns foo.main
  (:gen-class)

in your main source to generate the namespace package qualified class file. Add

:main foo.main
:manifest {"Class-Path" "lib/clojure-1.2.0.jar"}

to your Leiningen project file. After "lein jar" you can startup the application using the metadata from the JAR-embedded Manifest file:

java -jar foo-YOURVERSION.jar
like image 116
Jürgen Hötzel Avatar answered Oct 24 '22 01:10

Jürgen Hötzel


If you pack your application with leiningens uberjar task then all you need to do is run,

java -jar name-of-your-app.jar
like image 5
Hamza Yerlikaya Avatar answered Oct 24 '22 03:10

Hamza Yerlikaya


This is possible now [1] if you can generate a correct classpath (e.g. from Leiningen):

java -cp $(lein classpath) clojure.main -e "(do '(require '[clojure.string]) (println (clojure.string/join \" \" [1 2 3])))"

Or from an uberjar:

java -cp my_uberjar.jar clojure.main -e "(do '(require '[clojure.string]) (println (clojure.string/join \" \" [1 2 3])))"

You can also do something similar from another Clojure process itself (e.g. the repl) using this library https://github.com/clojure/java.classpath

(clojure.java.shell/sh "java" "-cp" (clojure.string/join ":" (map #(.toString %) (clojure.java.classpath/classpath) "clojure.main" :in (pr-str '(do (require '[my.namespace]) ([my.namespace/my-main)))))

[1] Not sure when this was introduced

like image 2
Jeroen van Dijk Avatar answered Oct 24 '22 03:10

Jeroen van Dijk