代码之家  ›  专栏  ›  技术社区  ›  devops

MongoDB Spring数据-将文档id应用于子对象id文件

  •  0
  • devops  · 技术社区  · 6 年前

    请查看以下Mongo DB文档:

    @Document(collection = CitizenForumMessageDocument.COLLECTION_NAME)
    public class ImageDocument {
    
        public static final String COLLECTION_NAME = "images";
    
        @Id
        private String      id;   // autogenerated 
        private Image       data; // data for the client (web, mobile...)
        private ImageMeta   meta; // for internal application work (uploader ip, etc...)
    
        [...] // getter, setter
    
    }
    
    // send as is to a client
    public class Image {
    
        private String id;
    
        [...]
    }
    

    是否可以将文档id应用于 Image 文档创建时的id。

    我现在的做法:

    public void saveUploadedImage(Client client, ImageForm form) {
    
        ImageDocument doc = new ImageDocument();
    
        dao.save(doc); // create document cause we need an id...
    
        try {
            doc.setImage(createImage(form, doc.getId()));
            doc.setMeta(createMeta(client, form));
        } catch(Exception e){
            dao.remove(doc);
            return; // ugly...
        }
    
        dao.update(doc);
    }
    

    我也可以通过在dao层中使用一些反射黑客来实现这一点,但我希望有更好的解决方案来解决这个问题。

    1 回复  |  直到 6 年前
        1
  •  1
  •   pvpkiran    6 年前

    您可以使用Mongo Lifycycle Events 为了这个。

    @Component
    public class MongoListener extends AbstractMongoEventListener<ImageDocument>
    {
    
      private final MongoTemplate mongoTemplate;
    
      @Autowired
      public MongoListener(final MongoTemplate mongoTemplate) {
        this.mongoTemplate = mongoTemplate;
      }
    
      @Override
      public void onAfterSave(AfterSaveEvent<ImageDocument> event) {
    
        ImageDocument imageDocument = event.getSource();
        if(imageDocument.getData().getId() == null) {
          imageDocument.getData().setId(imageDocument.getId());
          mongoTemplate.save(imageDocument);
        }
      }
    }
    

    我不得不说,这很难看,因为每次保存都会有两个数据库调用。

    但我看不到任何其他方法可以做到这一点。