Platinum Partner
java,languages,tips and tricks,clojure

Configuration Files in Clojure

I recently made a contribution to ghijira, a small tool written in Clojure for exporting issues from GitHub in JIRA-compatible format. One of the problems to solve there was loading configuration from file.

Originally, it used have a separate config.clj file that looked like this:

(def auth "EMAIL:PASS")
(def ghuser "user-name")
(def ghproject "project-name")
(def user-map
  { "GithubUser1" "JIRAUser1"
    "GithubUser2" "JIRAUser2"})

Then it was imported in place with:

(load-file "config.clj")

 

I did not like it, because it did not feel very functional and the configuration file had too much noise (isn’t def form manipulation too much for a configuration file?).

For a moment I thought about using standard Java .properties files. They get the job done, but they’re also somewhat rigid and unwieldy.

It occurred to me I really could use something similar to Leiningen and its project.clj files: Make the config a plain Clojure map. It’s very flexible with minimal syntax, and it’s pure data just like it should be.

From a quick Google search I found the answer at StackOverflow.

It turns out I can rewrite my configuration file to:

{:auth      "EMAIL:PASS"
 :ghuser    "user-name"
 :ghproject "project-name"
 :user-map
   { "GithubUser1" "JIRAUser1"
     "GithubUser2" "JIRAUser2" }
}

And then load it in Clojure with read:

(defn load-config [filename]
  (with-open [r (io/reader filename)]
    (read (java.io.PushbackReader. r))))

That’s it, just call read.

I find this solution a lot more elegant and “pure”.

By the way, this data format is getting a life of its own, called Extensive Data Notation. The Relevance team has even published a library to use EDN in Ruby.

 

 

 

 

 

Published at DZone with permission of {{ articles[0].authors[0].realName }}, DZone MVB. (source)

Opinions expressed by DZone contributors are their own.

{{ tag }}, {{tag}},

{{ parent.title || parent.header.title}}

{{ parent.tldr }}

{{ parent.urlSource.name }}
{{ parent.authors[0].realName || parent.author}}

{{ parent.authors[0].tagline || parent.tagline }}

{{ parent.views }} ViewsClicks
Tweet

{{parent.nComments}}