javascriptでobjectのpathを列挙するサンプル

javascriptでObjectを全部舐めてpathを全て列挙する必要があったのでサンプルを作成してみました。

パス列挙関数

/**
 * オブジェクトを再帰で探索し全ての終端までのパスをドット区切りで列挙
 * @param {object} obj 探索対象Object
 * @param {string} path パス
 */
var getPaths = function(obj, path){
    // Objectでなければ終端とみなす
    if(!(obj instanceof Object)){
         return [path];
    }
    // パス列挙用Array
    var paths = []
    // オブジェクトLoop
    Object.keys(obj).forEach(function(key){
        // 直接設定したプロパティでなければ対象外
        if(!obj.hasOwnProperty(key)){
            return;
        }
        // 返却されたパス列挙Arrayを結合
        paths = paths.concat(getPaths(obj[key], path ? path + "." + key : key));
    });
    // パス列挙Arrayを返却
    return paths;
};

参考

obj instanceof Object

developer.mozilla.org 下記とてもわかりやすいBlog、今回はArrayとObjectを探索したいので instanceof ObjectでOK

  1. typeofとinstanceofについてまとめ tweeeety.hateblo.jp

obj.hasOwnProperty(key)

developer.mozilla.org

paths.concat

developer.mozilla.org

path ? path + "." + key : key

developer.mozilla.org

動作サンプル

これ

var A = function(data) {
    this.data = {};
    if(data) {
    this.data = data;
  }
};

var B = function(data) {
    this.data = {};
    if(data) {
    this.data = data;
  }
};

var a1 = new A({Aa: 1, Ab: 2, Ac: 3});
var b1 = new B({Ba: 4, Bb: 5, Bc: 6});
var a2 = new A({Aa: 7, Ab: 8, Ac: 9});
var b2 = new B({Ba: 10, Bb: 11, Bc: 12});

var obj = {
    p1: a1,
  p2: 10,
  p3: {
    p31: a2,
    p32: 20,
  },
  p4: {
    p5: {
        p6: b2
    }
  },
  p5: [
    {p51: 1},
    {p52: 2},
  ],
  p6: "test",
};

console.log(getPaths(obj));

のように実行すると

[
     "p1.data.Aa"
    ,"p1.data.Ab"
    ,"p1.data.Ac"
    ,"p2"
    ,"p3.p31.data.Aa"
    ,"p3.p31.data.Ab"
    ,"p3.p31.data.Ac"
    ,"p3.p32"
    ,"p4.p5.p6.data.Ba"
    ,"p4.p5.p6.data.Bb"
    ,"p4.p5.p6.data.Bc"
    ,"p5.0.p51"
    ,"p5.1.p52"
    ,"p6"
]

となります。

JSFiddleの実行サンプル jsfiddle.net