Here is a simplified schema of my MongoDB doc:
{
"_id": 0,
"config": [{
"property1": "a",
"property2": "b",
"property3": "c",
"property4": "d"
},
{
"property1": "a",
"property2": "bb",
"property3": "cc",
"property4": "d",
"ispropert5": true
},
{
"property1": "a",
"property2": "b",
"property3": "c",
"property4": "ddd",
"ispropert5": false,
"ispropert6": false
}
],
"entity": "123asdf",
"url": "",
"createdDate": 1
}
As an output I need to get a list of unique keys of nested documents: {property1, property2, property3, property4, ispropert5, ispropert6}
I am trying this in my class but of course failing to cast ArrayList to Document:
Document dbo = col.find().first();
Set<String> keys = dbo.keySet();
Iterator iterator = keys.iterator();
while(iterator.hasNext()) {
String key = iterator.next().toString();
if(dbo.get(key) instanceof ArrayList){
Document dboNested = (Document) dbo.get(key); //java.lang.ClassCastException: java.util.ArrayList cannot be cast to org.bson.Document
Set<String> keysNested = dboNested.keySet();
System.out.println("KeyNested: " + keysNested);
}
}
Like you've commented, on your code, you cannot convert ArrayList to Document, therefore you must cast it to an ArrayList like below:
while(iterator.hasNext()) {
String key = iterator.next().toString();
Object value = dbo.get(key);
if (value instanceof ArrayList){
ArrayList<?> dboArrayNested = (ArrayList<?>) value;
for (Object dboNestedObj : dboArrayNested) {
if (dboNestedObj instanceof Document) {
printKeysNested(Document.class.cast(dboNestedObj));
}
}
// else if extra...
} else if (value instanceof Document) {
printKeysNested(Document.class.cast(value));
}
}
public static void printKeysNested(Document dboNested) {
Set<String> keysNested = dboNested.keySet();
System.out.println("KeyNested: " + keysNested);
}
I hope this helps you.
I guess i am late here, but i was trying a more mongo way to do this. You would definitely want to execute this on a small set of query, may be a match
stage before even starting this
db.coll.aggregate([{
$unwind: '$config'
}, {
$project: {
arr: {
$objectToArray: '$config'
}
}
}, {
$unwind: '$arr'
}, {
$group: {
_id: {
key: '$arr.k'
}
}
}, {
$project: {
key: '$_id.key',
_id: 0
}
}
])
thanks to all the answers, here is the final code I have:
while (iterator.hasNext()) {
String key = iterator.next().toString();
Object value = dbo.get(key);
if (value instanceof ArrayList) {
ArrayList<?> dboArrayNested = (ArrayList<?>) value;
for (Object dboNestedObj : dboArrayNested) {
Document dboNested = Document.class.cast(dboNestedObj);
if (dboNestedObj instanceof Document) {
keysNested.addAll(dboNested.keySet());
}
}
// else if extra...
} else if (value instanceof Document) {
Document dboNested = Document.class.cast(value);
keysNested.addAll(dboNested.keySet());
}
}
System.out.println("KeysNested: " + keysNested);
this outputs for the given example: [property1, property2, property3, property4, ispropert5, ispropert6]
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.