使用spring数据mongo Upsert Mongo Document

时间:2016-02-05 09:18:19

标签: spring spring-boot spring-data spring-data-mongodb spring-data-rest

我有一个班级

@Document
public class MyDocument {
   @Id
   private String id;
   private String title;
   private String description;
   private String tagLine;

   @CreatedDate
   private Date createdDate;

   @LastModifiedDate
   private Date updatedDate;

   public String getId() {
     return id;
   }
   public void setId(String id) {
     this.id = id;
   }

   public String getTitle() {
     return title;
   }

   public void setTitle(String title) {
     this.title = title;
   }

   public String getDescription() {
     return description;
   }

  public void setDescription(String description) {
    this.description = description;
  }
  public String getTagLine() {
     return tagLine;
   }

  public void setTagLine(String tagLine) {
    this.tagLine = tagLine;
  }
}

我添加了带@EnableMongoAuditing

的带注释的应用程序

我创建了实现mongorepository的接口

public interface MyDocumentRepository extends MongoRepository<MyDocument, String> { }

当我使用GETPOSTPATCH方法创建RestController时 在POST我正在发送 {'title':'first'}

Controller Class POST方法是

@RequestMapping(value = "/", method = RequestMethod.POST)
public ResponseEntity<?> saveMyDocument(@RequestBody MyDocument myDocument) { 
   MyDocument doc = myDocumentRepo.save(myDocument);
   return new ResponseEntity<MyDocument>(doc, HttpStatus.CREATED);
}

它将数据保存在mongo中。

{
    "_id" : ObjectId("56b3451f0364b03f3098f101"),
    "_class" : "com.wiziq.service.course.model.MyDocument",
    "title" : "test"
}

和PATCH请求就像

@RequestMapping(value = "/{id}", method = RequestMethod.PATCH)
public ResponseEntity<MyDocument> updateCourse(@PathVariable(value = "id") String id,
        @RequestBody MyDocument myDocument) {
    myDocument.setId(id);
    MyDocument doc = courseService.save(myDocument);
    return ResponseEntity.ok(course);
}

在使用数据{"description":"This is test"}制作PATCH请求时 它更新了docuent BUT 它删除了标题字段和createdDate形成文档,它正在做更新,这是好的。但我想做一个upsert,我可以使用mongoTemplate, 但是我必须设置我想要设置的每个属性。

如果我收到PATCH请求,是否有任何通用的方法我只能更新非属性..请求中的属性

spring-data-rest似乎是使用@RepositoryRestResource来做的。我怎样才能实现同样的目标。

我不想这样编码 Update update = new Update().set("title", myDocument.getTitle()).set("description", myDocument.getdescription());

2 个答案:

答案 0 :(得分:2)

不幸的是它在MongoDB中的行为,你可以使用shell验证相同。 所以更新创建一个更新对象并使用

Query query = new Query(Criteria.where("id").is(ID)); 

此处ID是您要更新的文档。根据您的要求设置upsert,然后使用findAndModify更新文档。

mongoTemplate.findAndModify(query, update,
                new FindAndModifyOptions().returnNew(true).upsert(false),
                someclass.class);

答案 1 :(得分:0)

如果您有一个类似MyModel.class的模型,并且需要一种从中创建Update对象的简便方法,则没有真正明确的方法,但是可以使用在Spring Data Mongo自动配置中创建的MongoConverter bean然后只需使用MongoCollection的replaceOne方法即可。

@Autowired
private MongoTemplate template;
@Autowired
private MongoConverter mongoConverter;

...

@Override
public void upsertMyModel(MyModel model) {
    Document documentToUpsert = new Document();
    mongoConverter.write(model, documentToUpsert);
    template.getCollection(collectionName).replaceOne(
            Filters.eq("_id", model.getId()),
            documentToUpsert,
            new ReplaceOptions().upsert(true));
}