Skip to content


Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse files

Removing the :required option. Hangover from when -h and --help were

implemented by default, causes problems if you want help and dont
provide a :required argument.
  • Loading branch information...
commit 47984bc7413d7a675ea9586d08d461d4a016060e 1 parent 3c57cc5
@gar3thjon3s gar3thjon3s authored
@@ -5,7 +5,7 @@ tools.cli is a command line argument parser for Clojure.
## An Example
(cli args
- ["-p" "--port" "Listen on this port" :required true :parse-fn #(Integer. %)]
+ ["-p" "--port" "Listen on this port" :parse-fn #(Integer. %)]
["-h" "--host" "The hostname" :default "localhost"]
["-v" "--[no-]verbose" :default true]
["-l" "--log-directory" :default "/some/path"])
@@ -34,12 +34,12 @@ and a documentation string to use to provide help:
- Switches Default Required Desc
- -------- ------- -------- ----
- -p, --port Yes Listen on this port
- -h, --host localhost No The hostname
- -v, --no-verbose --verbose true No
- -l, --log-directory /some/path No"
+ Switches Default Desc
+ -------- ------- ----
+ -p, --port Listen on this port
+ -h, --host localhost The hostname
+ -v, --no-verbose --verbose true
+ -l, --log-directory /some/path
## Options
@@ -62,13 +62,12 @@ This will be printed in the 'Desc' column of the help banner.
Following that are optional parameters, provided in key-value pairs:
- ["-p" "--port" "The port to listen on" :default 8080 :parse-fn #(Integer. %) :required true]
+ ["-p" "--port" "The port to listen on" :default 8080 :parse-fn #(Integer. %)]
These should be self-explanatory. The defaults if not provided are as follows:
{:default nil
:parse-fn identity
- :required false
:flag false}
### Boolean Flags
18 src/main/clojure/clojure/tools/cli.clj
@@ -4,25 +4,24 @@
[clojure.pprint :only (pprint cl-format)])
(:refer-clojure :exclude [replace]))
-(defn build-doc [{:keys [switches docs default required]}]
+(defn build-doc [{:keys [switches docs default]}]
[(apply str (interpose ", " switches))
(or (str default) "")
- (if required "Yes" "No")
(or docs "")])
(defn banner-for [specs]
(println "Usage:")
(let [docs (into (map build-doc specs)
- [["--------" "-------" "--------" "----"]
- ["Switches" "Default" "Required" "Desc"]])
+ [["--------" "-------" "----"]
+ ["Switches" "Default" "Desc"]])
max-cols (->> (for [d docs] (map count d))
(apply map (fn [& c] (apply vector c)))
(map #(apply max %)))
vs (for [d docs]
(mapcat (fn [& x] (apply vector x)) max-cols d))]
(doseq [v vs]
- (cl-format true "~{ ~vA ~vA ~vA ~vA ~}" v)
+ (cl-format true "~{ ~vA ~vA ~vA ~}" v)
(defn name-for [k]
@@ -103,22 +102,13 @@
:name (keyword (last aliases))
:parse-fn identity
:default (if flag false nil)
- :required false
:flag flag}
-(defn ensure-required-provided
- [m specs]
- (doseq [s specs
- :when (s :required)]
- (when-not (m (s :name))
- (throw (Exception. (str (s :name) " is a required argument"))))))
(defn cli
[args & specs]
(let [specs (map generate-spec specs)]
(let [[options extra-args] (apply-specs specs args)
banner (with-out-str (banner-for specs))]
- (ensure-required-provided options specs)
[options extra-args banner])))
10 src/test/clojure/clojure/tools/cli_test.clj
@@ -52,16 +52,6 @@
(first (cli ["-s" "localhost"]
["-s" "--server"]))))))
- (testing "required"
- (deftest should-succeed-when-provided
- (cli ["--server" "localhost"]
- ["--server" :required true]))
- (deftest should-raise-when-missing
- (is (thrown-with-msg? Exception #"server is a required argument"
- (cli []
- ["--server" :required true])))))
(testing "extra arguments"
(deftest should-provide-access-to-trailing-args
(let [[options args _] (cli ["--foo" "bar" "a" "b" "c"]
Please sign in to comment.
Something went wrong with that request. Please try again.