private Object negate(Document arg) {
        List<Object> list = new ArrayList<Object>();
        for (Map.Entry<String, Object> entry : arg.entrySet()) {
            if (entry.getKey().equals("$or")) {
                list.add(asDocument("$nor", entry.getValue()));

            } else if (entry.getKey().equals("$and")) {
                List<Object> list2 = new ArrayList<Object>();
                for (Object o : ((Collection) entry.getValue())) {
                    list2.add(negate((Document) o));
                }
                list.add(asDocument("$or", list2));

            } else if (entry.getValue() instanceof Pattern || entry.getValue() instanceof BsonRegularExpression) {
                list.add(asDocument(entry.getKey(), asDocument("$not", entry.getValue())));

            } else if (entry.getValue() instanceof Document) {
                list.add(negate(entry.getKey(), (Document) entry.getValue()));

            } else {
                list.add(asDocument(entry.getKey(), asDocument("$ne", entry.getValue())));
            }
        }
        return list.size() == 1 ? list.get(0) : asDocument("$or", list);
    }
Serializes the given Querydsl query to a Document query for MongoDB.

@author Mark Paluch
querydsl-mongodb/src/main/java/com/querydsl/mongodb/document/MongodbDocumentSerializer.java