clojure实战——配置文件

来源:互联网 发布:印度火星探测器 知乎 编辑:程序博客网 时间:2024/05/21 08:01
使用clojure开发时,被它灵活、简单的配置形式给惊艳到了!当然,我这里不是说各种复杂的组件之间的配置,而是一些
简单的、用于程序内部逻辑的一些配置。因为自己在使用clojure时,用各种组件构建复杂的服务的经验尚少,就不敢妄语。
这里主要针对自己在项目开发工程中用到的部分做讲解。

clojure配置的方式大致有两种(当然,github也有一些开源包定义自己配置方式):.edn文件和.clj文件。


1. .edn形式配置

1.1 .edn文件格式

.edn文件其实就是一个静态文本文件配置。要使用这种配置形式,你只理解Map这一种数据结构!也就是说,.edn文件中必

须是一堆key-value的map格式,可嵌套。

下面以一个具体的配置文件举例说明,如下config.edn:

{; .edn文件支持注释,因而可以就地添加配置说明,方便维护。 ; .edn文件主要是map的key-value格式,其中value可以有复杂的数据类型 ; (1)value为简单类型String、int、float等 :name "b" :age 20 :length 1.76 ; (2)value为map类型 :rpc-server {:host "127.0.0.1" :port 8015 :log-level :debug} ; (3)value为set类型,注意:set要遵循java集合类型Set的规则,不能重复,类型一致 :set-config1 #{1 2 3} :set-config2 #{:a :b :c} ; (4)value为数组类型,用"[]"表示 :arr-config [1 2 3 4] ; (5)各类型间可相互组合,嵌套,如: :students [{:name1 "a" :age 20}            {:name1 "b" :age 20}            {:name1 "c" :age 20}]}

clojure在读入.edn文件时,会判断其value的类型,进而将其转换为对应的数据类型。

:name "b"中"b"在内存中会是String类型,"[]"为数组,"#{}"为set集合,所以你可以用clojure处理这些类型的方法取处理这些

数据。完全是无缝连接,非常方便。但要注意一点:clojure读入.edn文件时,不会对配置的算术表达式进行运算。如你不能

配置":age (+ 1 2)",而期待clojure会帮你处理为":age 3"

1.2 读入.edn文件

要读入文件,首先要用到clojure.java.io单元,该单元用于读入文件到内存。其次使用clojure.edn单元,该单元会将.edn文件

中的各种value转换为对应类型的值。最后,你就可以在程序中像是使用clojure的map类型数据一样使用你得配置啦!


读取.edn配置代码如下:

(ns util.readedn  (:require [clojure.java.io :as cio]            [clojure.edn :as edn]))(defn load-edn-config  "加载edn配置文件"  [edn-filename]  (with-open [in-edn (-> edn-filename                         cio/resource                         cio/reader                         (java.io.PushbackReader.))]    (clojure.edn/read in-edn)))

使用举例:

(ns example  (:require [util.readedn :as util])  (defn read-edn-eg []  (let [conf (util/load-edn-config "etc/config.edn")]    (:name conf)))

该函数应该返回name的值“b”(代码简单,未测试)。


2. .clj配置形式

2.1 .clj配置格式

.clj文件其实和clojure工程中其他.clj一样,其书写格式必须满足clojure编程的语法,只是.clj放入到资源文件夹时,就被当成资源文件进行修改、配置。

.clj文件与其他clojure工程文件一样,可以在里面定义函数、运算、函数调用等等。但建议不要过于复杂,不然就失去配置文件的本来意义。

如config.clj:

(ns config)(def config1       {:a "a" :b "b"})(def config2       {:a (+ 1 2)       :b (fn [arg1] (prn (str arg1))       :c (fn [arg2] <pre name="code" class="java">

可以看出,它和普通的.clj文件一样有命名空间,遵从clojure语法。

2.2 使用.clj配置文件

.clj配置文件使用时非常简单,就像引用普通.clj文件一样,(:require [config])。

如:

(ns test  (:require [config]))(defn get-config []   (-> config/config2         :a))               (let [a 3]                  (+ a 4))})

函数get-config应该返回3,即“:a (+ 1 2)”对应的配置值。

被当成资源文件的.clj文件在修改之后不用再编译整个功能,只需重新启动服务,就能将修改加载到程序中。


3. 总结

使用那种配置格式,根据项目需要选择。

通常来说,如果只是静态值的配置,建议使用.edn文件形式,因为.clj形式的配置文件在使用时,是作为一个普通的.clj文件导入的,耦合太紧。

而如果想要配置简单逻辑、动态输出等,用.clj的方式会非常方便(这是用java等语言所没有的便捷)。

如果你的程序设计得足够好,完全可以通过配置来修改程序的部分逻辑,从而使同一个框架代码产出不同的效果!


用clojure已一年,一直也没有很深入去研究这么语言,只是在工作中要用到的时候,再去查阅资料,现学现卖,也能把项目完成~(不知不觉也学会很多)。其实一直纠结于学clojure是否有用,因为目前国内使用clojure开发的公司还是很少,对于以后的职业发展是否有利,有点困惑。不过最近在一些论坛看到有很多人也在学习clojure(貌似很多都没有自己学的好\(^o^)/~),有些公司也在使用clojure,招聘网上也有零星clojure工程师招聘...就觉得clojure也是一门可以用于吃饭的语言^ ^。再者,在实际应用中,发现clojure做服务器端有时开发效率当真很快,代码也优雅...学学也是蛮有价值的。另外,发现clojure的中文资料还是很少,特别是对其实际应用的中文资料,因此决定好好总结一下clojure在一些实际项目中的应用,贡献微薄经验,希望于他人有所帮助。


0 0