Morphia MongoDB 检查空和不存在的字段

问题描述:

我是 Morphia 和 MongoDB 的新手.有没有办法使用 Morphia 检查我的数据库中的某个字段是否不是 null 并且也存在.例如,来自数据库中用户集合的用户的以下记录:

I am new to both Morphia and MongoDB. Is there a way to check using Morphia that a certain field in my database is not null and also exists. For example from the following record of a user from a collection of users in database:

{ "_id" : ObjectId("51398e6e30044a944cc23e2e"), 
  "age" : 21 , 
  "createdDate" : ISODate("2013-03-08T07:08:30.168Z"),
  "name" : "Some name" }

我将如何使用 Morphia 查询来检查字段 "createdDate" 是否为空且存在.

How would I use a Morphia query to check if field "createdDate" is not null and exists.

我正在寻找 Morphia 的解决方案.到目前为止,我想出了这个:

I am looking for a solution in Morphia. So far I have come up with this:

query.and(query.criteria("createdDate").exists(),
query.criteria("createdDate").notEqual(null));

从文档中,我了解到 Morphia 不存储空字段或空字段.因此 notEqual(null) 的理由.

From documentation, I learnt Morphia does not store empty or null fields. Hence the justification for notEqual(null).

编辑 2: 从答案中我可以看出问题需要更多解释.我无法修改 createdDate.详细说明:上面的示例没有我的实际问题复杂.我的真正问题有我无法修改的敏感字段.同样让事情变得更复杂的是,我无法控制模型,否则我可以使用其中一个答案中建议的 @PrePersist.

EDIT 2: From the answers I can see the problem needs more explanation. I cannot modify the createdDate. To elaborate: the example above is less complex than my actual problem. My real problem has sensitive fields which I cannot modify. Also to complicate things a bit more, I do not have control over the model otherwise I could have used @PrePersist as proposed in one of the answers.

当我无法控制模型并且不允许修改字段时,有没有办法检查空字段和不存在的字段?

Is there a way to check for null and non existing field when I have no control over the model and I am not allowed to modify fields?

来自 文档,Morphia 不存储 Null/Empty 值(默认情况下)所以查询

From the documentation, Morphia does not store Null/Empty values (by default) so the query

query.and(
    query.criteria("createdDate").exists(),
    query.criteria("createdDate").notEqual(null)
);

将不起作用,因为您似乎无法查询 null,但可以查询特定值.

will not work since it seems you are not able to query on null, but can query for a specific value.

但是,由于您只能查询特定值,因此您可以设计一种解决方法,在其中使用模型中从未使用过的日期值更新 createdDate 字段.例如,如果您使用 0 初始化 Date 对象,它将被设置为纪元的开始,即 1970 年 1 月 1 日 00:00:00 UTC.您获得的小时数是本地化的时间偏移量.如果您的更新只涉及修改 mongo shell 中的匹配元素就足够了,因此它看起来类似于:

However, since you can only query for a specific value, you can devise a workaround where you can update the createdDate field with a date value that is never used in your model. For example, if you initialize a Date object with 0, it will be set to the beginning of the epoch, Jan 1st 1970 00:00:00 UTC. The hours you get is the localized time offset. It will be sufficient if your update only involves modifying the matching element(s) in mongo shell, hence it would look similarly to this:

db.users.update(
    {"createdDate": null }, 
    { "$set": {"createdDate": new Date(0)} }
)

然后您可以使用流畅界面 查询该特定值:

You can then use the Fluent Interface to query on that specific value:

Query<User> query = mongoDataStore
    .find(User.class)    
    .field("createdDate").exists()
    .field("createdDate").hasThisOne(new Date(0));

定义模型以包含更新 createdDate 字段的 prePersist 方法会简单得多.该方法使用 @PrePersist 注释标记,以便在保存订单之前在订单上设置日期.@PostPersist@PreLoad@PostLoad 存在等效的注释.

It would be much simpler when defining your model to include a prePersist method that updates the createdDate field. The method is tagged with the @PrePersist annotation so that the date is set on the order prior to it being saved. Equivalent annotations exist for @PostPersist, @PreLoad and @PostLoad.

@Entity(value="users", noClassNameStored = true)
public class User {

    // Properties
    private Date createdDate;

    ...
    // Getters and setters
    ..

    @PrePersist
    public void prePersist() {
        this.createdDate = (createdDate == null) ? new Date() : createdDate;
    }
}