以表格格式查询MongoDB嵌入式文档,而不是数组

时间:2017-11-14 16:38:14

标签: json mongodb mongodb-query

我将以下JSON导入MongoDB(mongoimport --host localhost --db test --collection employees --type json --file Employees.json --jsonArray)

[ 
    {
        "Employee" : {
            "Basics" : {
                "Name" : "James Bond",
                "Age" : 42
            },
            "Addresses" : {
                "Address" : {
                    "City" : "London",
                    "Country" : "England"
                },
                "Address" : {
                    "City" : "Paris",
                    "Country" : "France"
                }
            },
            "Cars" : {
                "Car" : {
                    "Model" : "Aston Martin",
                    "Year" : 1977
                },
                "Car" : {
                    "Model" : "Audi",
                    "Year" : 2000
                }
            }
        }
    },
    {
        "Employee" : {
            "Basics" : {
                ..
            },
            "Addresses" : {
                "Address" : {
                    ..
                },
                "Address" : {
                    ..
                }
            },
            "Cars" : {
                "Car" : {
                    ..
                }
            }
        }
    }
]

为了以表格格式获得结果,我使用了以下查询,但它只提取阿斯顿马丁而不是奥迪。

db.employees.aggregate( 
[
{$match: {'Employee.Basics.Name':{$eq:"James Bond"}}},
{$project: {carModel:'$Employee.Cars.Car.Model',_id:0}}
]); 
  1. 有没有办法可以同时获得这两个值? (以表格格式表示 具体领域 - 不喜欢 。db.getCollection('员工')找到({' Employee.Basics.Name':{$ EQ:"詹姆斯 邦德"}});)
  2. 看看其他示例,看起来JSON应该有一个汽车和地址阵列,有没有办法我可以更新MongoDB中的文件,现在将它们更改为数组?
  3. 我是MongoDB的新手,(仅仅2天大:) :)所以任何指针都会有很大的帮助。 提前谢谢!

1 个答案:

答案 0 :(得分:0)

如果有人在我的例子中有不正确的JSON,你可以使用下面的Java代码来修复它。 (我使用https://sourceforge.net/projects/xml2json-converter/获得了JSON)。

private final Deque<Integer> arrayStack = new ArrayDeque<Integer>();
private final Deque<Integer> arrayElemStack = new ArrayDeque<Integer>();

String[] arrayElemNames = {"Employee","Address","Car"};
String[] arrayNames = {"Addresses","Cars"};

public void cleanJSON() throws IOException {

    try (BufferedWriter writer = Files.newBufferedWriter(Paths.get(outputJsonFileName))) {
        try (Stream<String> stream = Files.lines(Paths.get(inputJsonFileName))) {
            stream.map((str) -> formatRootElem(str)).map((str) -> formatArrayElems(str))
                    .map((str) -> formatArrays(str)).forEach((str) -> writeToOutput(writer, str));
        }
    }

}

private void writeToOutput(BufferedWriter writer, String str) {
    try {
        writer.write(str + "\n");
    } catch (IOException e) {
        e.printStackTrace();
    }
}

private String formatRootElem(String str) {
    if (str.equals("{")) {
        return "[";
    } else if (str.equals("}")) {
        return "]";
    } else if ((str.contains("Employees") && str.contains("{")) || str.equals("  }")) {
        return "";
    }
    return str;
}

private String formatArrayElems(String str) {
    if (checkInArray(str, arrayElemNames)) {
        arrayElemStack.push(1);
        return "{" + str;
    }
    if (!arrayElemStack.isEmpty()) {
        if (str.contains("{")) {
            int count = arrayElemStack.pop();
            arrayElemStack.push(++count);
        } else if (str.contains("}")) {
            int count = arrayElemStack.pop();
            --count;
            if (count == 0) {
                str = str.replace("}", "}}");
            } else {
                arrayElemStack.push(count);
            }
        }
    }
    return str;
}

private String formatArrays(String str) {
    if (checkInArray(str, arrayNames)) {
        str = str.replace('{', '[');
        arrayStack.push(1);
    } else if (!arrayStack.isEmpty()) {
        if (str.contains("{")) {
            int count = arrayStack.pop();
            arrayStack.push(++count);
        } else if (str.contains("}")) {
            int count = arrayStack.pop();
            --count;
            if (count == 0) {
                str = str.replace('}', ']');
            } else {
                arrayStack.push(count);
            }
        }
    }
    System.out.println(str);
    return str;
}

private boolean checkInArray(String str, String[] strArray) {
    for (String arrayElem : strArray) {
        if (str.contains(arrayElem) && str.contains(":")) {
            return true;
        }
    }
    return false;
}