2017-04-07 8 views
0

クロージャーの大きな地図で特定のキーを変更したい。 これらのキーはマップのどのレベルにも存在できますが、常に必要なキーの範囲内にあります選択したキーワードのClojureケバブケース

私はcamel-snake-kebabライブラリを使用していましたが、必要なキー-key map。変更が

(def my-map {:allow_kebab_or-snake {:required-key {:must_be_kebab ""}} 
      :allow_kebab_or-snake2 {:optional-key {:required-key {:must_be_kebab ""}}}}) 

が現在/徒歩/ postwalkは、交換するが、それは内にネストされていないキーを変更することが恐れる使用してJSONまたはマップで行われるかどうかは関係ありません:必要なキーマップ

(walk/postwalk-replace {:must_be_kebab :must-be-kebab} my-map)) 

答えて

0

ummmm ..明らかにできましたか:マップのキーを変更しますか?または関連する値?オフトピック

:上記のマップが正しくありません: -

postwalk-置き換える(二つの同一のキー持つallow_kebab_or_snakeをあなただけのポイントを強調して:)実際の例を示していないと仮定すると、IM)は、任意に置換されますその値を持つキーの発生。

(walk/postwalk-replace {:must_be_kebab :mus-be-kebab} 
         (get-in my-map [:allow_kebab_or_snake :required-key])) 

をしかし、その後、あなたはあなたの初期にassocこのする必要があります:

あなたが最初のget-中であなたのサブ構造体を選択して使用することができ、正確なマップ構造体を知っていればそうpostwalkをリプレース地図。

また、インタリーブされたDSが複雑すぎる場合は、ウォーク機能を考慮して独自のアルゴリズムを構築する必要があります。

+0

おかげで、を見てくださいJsonペイロードにはスネークケースがありますが、ケバブが必要です。 –

0

ここに解決策があります。コンバージョンが発生するかどうかを制御する必要があるため、postwalkだけを使用することはできません。あなた自身の再帰を実装し、あなたの条件が見つかったときに非変換→変換からコンテキストを変更する必要があります。

(ns tst.clj.core 
    (:use clj.core clojure.test tupelo.test) 
    (:require 
    [clojure.string :as str] 
    [clojure.pprint :refer [pprint]] 
    [tupelo.core :as t] 
    [tupelo.string :as ts] 
)) 
(t/refer-tupelo) 
(t/print-versions) 

(def my-map 
    {:allow_kebab_or-snake {:required-key {:must_be_kebab ""}} 
    :allow_kebab_or-snake2 {:optional-key {:required-key {:must_be_kebab ""}}}}) 

(defn children->kabob? [kw] 
    (= kw :required-key)) 

(defn proc-child-maps 
    [ctx map-arg] 
    (apply t/glue 
    (for [curr-key (keys map-arg)] 
     (let [curr-val (grab curr-key map-arg) 
      new-ctx (if (children->kabob? curr-key) 
         (assoc ctx :snake->kabob true) 
         ctx) 
      out-key (if (grab :snake->kabob ctx) 
         (ts/kw-snake->kabob curr-key) 
         curr-key) 
      out-val (if (map? curr-val) 
         (proc-child-maps new-ctx curr-val) 
         curr-val)] 
     {out-key out-val})))) 

(defn nested-keys->snake 
    [arg] 
    (let [ctx {:snake->kabob false}] 
    (if (map? arg) 
     (proc-child-maps ctx arg) 
     arg))) 

最終結果は、ユニットテストで示されている:このソリューションの

(is= (nested-keys->snake my-map) 
    {:allow_kebab_or-snake 
    {:required-key 
     {:must-be-kebab ""}}, 
    :allow_kebab_or-snake2 
    {:optional-key 
     {:required-key 
     {:must-be-kebab ""}}}})) 

Iの又はしなくてもよいフィールド提案のちょうど左側便宜機能in the Tupelo library.

0

のいくつかを使用しました作業。これは、 ' - 'が予約語として認識され、識別子で使用できないため、SQLデータベースを扱うときに発生する問題です。ただし、clojureを使用する場合はキーワードに ' - 'を使用するのが一般的です。 clojureでSQLを操作する際に使用される多くの抽象レイヤーは、準備文などの引数/バインディングとしてマップを取得します。 SQLへ行くかsqlから。このaproachの利点は、コンバージョンを作るマップを歩いていません - 。あなたはオンザフライ変換」を行う」ことが必要とされるとき

は、私はケバブするキーを変更する必要がhttps://pupeno.com/2015/10/23/automatically-converting-case-between-sql-and-clojure/

関連する問題