如何重构这个 clojure / riemann 代码

How to refactor this clojure / riemann code

我是 discovering/learning Clojure with Riemann,我编写了以下代码来汇总每个主机的 CPU 指标:

(streams
 (by [:host]
     smap (aggregate-cpu-metrics "user" folds/mean)
     smap (aggregate-cpu-metrics "nice" folds/mean)
     smap (aggregate-cpu-metrics "system" folds/mean)
     smap (aggregate-cpu-metrics "idle" folds/mean)
     smap (aggregate-cpu-metrics "wait" folds/mean)
     smap (aggregate-cpu-metrics "interrupt" folds/mean)
     smap (aggregate-cpu-metrics "softirq" folds/mean)
     smap (aggregate-cpu-metrics "steal" folds/mean)))


(defn aggregate-cpu-metrics
  [name, aggr]
  (where (service (re-pattern (str "cpu-[0-9]+ " name)))
      (coalesce 10
          (smap aggr
              (with :service (str "cpu-average " name) reinject)))))

为了稍微解释一下代码,我收到了这样的事件:

我的目标是计算平均值并将此事件重新注入黎曼:

它正在运行,这不是问题所在。 但是正如您在第 3 行到第 10 行中看到的,这里有很多重复代码。我正在寻找重构此代码的方法,但我被卡住了。

我想用我的指标名称定义一个向量:

(def cpu-metrics ["user", "nice", "system", "idle", "interrupt", "softirq", "steal"])

...并用它来调用 smap(aggregate-cpu-metrics...

但我不知道该怎么做。我试过 mapdoseq,但没有成功。

你会怎么做?

(更新/解决方案)

这是我在阅读 Arthur 的回答后重构的版本。

(streams
 (where
  (service #"^cpu-[0-9]+ ")
  (adjust
   [:service #(clojure.string/replace % #"^cpu-[0-9]+" "cpu-average")]
   (by [:host :service]
       (fixed-time-window 10 (smap folds/mean reinject))))))

我可能会通过首先提取名称并创建新的服务名称,然后使用服务名称和主机来拆分事件流,从而将函数稍微翻个底朝天。

像这样:

(streams 
   (where (service #"cpu-[0-9]+ ")
     (adjust [:service (fn [service] 
                         (str "cpu-average "
                              (second (clojure.string/split service #"cpu-[0-9]+ "))))]
       (by [:host :service]  ...  )))

这有一个副作用,即允许任何 cpu 报告的服务在不更改监控代码的情况下显示在统计信息中。如果你不想要这个,你可以添加另一个 where 来明确接受你想要的。我这里没有设置来测试这个所以如果代码损坏请编辑:-)