Hướng dẫn mongodb timestamp spring boot - khởi động mùa xuân dấu thời gian mongodb

Ứng dụng này đang đồng bộ hóa các bản ghi dữ liệu giữa các thiết bị thông qua bộ sưu tập DB Mongo trực tuyến. Nhiều thiết bị có thể gửi hàng loạt các bản ghi mới hoặc sửa đổi đến bộ sưu tập của máy chủ Mongo bất cứ lúc nào. Các thiết bị nhận được tất cả các bản cập nhật bản ghi cho họ mà họ chưa có, bằng cách yêu cầu các bản ghi được thêm hoặc sửa đổi kể từ khi nhận được yêu cầu cuối cùng của họ.

Cách tiếp cận 1 - là thêm một trường đối tượng ngày (được gọi là Stored1) vào các bản ghi trước khi lưu vào MongoDB. Khi một thiết bị yêu cầu các bản ghi, phân trang MongoDB được sử dụng để bỏ qua các mục nhập vào trang hiện tại và sau đó giới hạn là 1000. Bây giờ bộ dữ liệu lớn, mỗi yêu cầu trang đang mất nhiều thời gian và Mongo đã gặp lỗi bộ nhớ. https://docs.mongodb.com/manual/reference/limits/#operations
https://docs.mongodb.com/manual/reference/limits/#operations

Cài đặt allowdiskuse (true) như được hiển thị trong mã đã đăng trong cấu hình hiện tại của tôi không sửa lỗi bộ nhớ vì một số lý do. Nếu điều đó có thể được sửa chữa, nó vẫn không phải là một giải pháp lâu dài vì thời gian truy vấn với phân trang đã quá dài.

Tiếp cận 2:

Cách tốt nhất để phân trang trên MongoDB bằng cách sử dụng Java

https://arpitbhayani.me/blogs/benchmark-and-compare-pagination-approach-in-mongodb

Cách tiếp cận thứ 2 được coi là thay đổi từ các bản ghi phân trang Mongo đã trả lại, để chỉ yêu cầu thời gian lưu trữ> thời gian lưu trữ lớn nhất nhận được lần cuối, cho đến khi số lượng hồ sơ trong một lần trả lại thấp hơn giới hạn. Điều này đòi hỏi dấu thời gian được lưu trữ phải là duy nhất giữa tất cả các bản ghi khớp với truy vấn hoặc nó có thể bỏ lỡ các bản ghi hoặc nhận bản ghi trùng lặp, v.v. .

Mongo có dấu thời gian BSON đảm bảo các giá trị duy nhất cho mỗi bộ sưu tập, nhưng tôi không thấy cách sử dụng nó với tài liệu lưu () hoặc truy vấn trên nó trong Spring Boot. Nó sẽ cần được đặt trên mỗi bản ghi mới được chèn hoặc thay thế hoặc cập nhật. https://docs.mongodb.com/manual/reference/bson-types/#timestamp

Có bất cứ đề nghị nào cho việc làm như thế này hả?

@Getter
@Setter
public abstract class DataModel {

    private Map<String, Object> data;

    @Id // maps this field name to the database _id field, automatically indexed
    private String uid;

    /** Time this entry is written to the db (new or modified), to support querying for changes since last query */
    private Date stored1; //APPROCAH 1
    private long stored2; //APPROACH 2
}

/** SpringBoot+MongoDb database interface implementation */
@Component
@Scope("prototype")
public class SpringDb implements DbInterface {

    @Autowired
    public MongoTemplate db; // the database

    @Override
    public boolean set(Collection<?> newRecords, Collection<?> updatedRecords) {
        // get current time for this set
        Date date = new Date();
        int randomOffset = ThreadLocalRandom.current().nextInt(0, 500000);
        long startingNanoSeconds = Instant.now().getEpochSecond() * 1000000000L + instant.getNano() + randomOffset;
        int ns = 0;

        if (updatedRecords != null && updatedRecords.size() > 0) {
            for (Object entry : updatedRecords) {
                entry.setStored1(date); //APPROACH 1
                entry.setStored2(startingNs + ns++); //APPROCH 2
                db.save(entry, repoName);
            }
        }

        // for new documents only
        if (newRecords != null && newRecords.size() > 0) {
            for (DataModel entry : newRecords) {
                entry.setStored1(date); //APPROACH 1
                entry.setStored2(startingNs + ns++); // APPROACH 2
            }
    
            //multi record insert
            db.insert(newRecords, repoName);
        }

        return true;
    }

    @Override
    public List<DataModel> get(Map<String, String> params, int maxResults, int page, String sortParameter) {
        // generate query
        Query query = buildQuery(params);

        //APPROACH 1 
        // do a paged query
        Pageable pageable = PageRequest.of(page, maxResults, Direction.ASC, sortParameter);
        List<T> queryResults = db.find(query.allowDiskUse(true).with(pageable), DataModel.class, repoName); //allowDiskUse(true) not working, still get memory error
        // count total results
        Page<T> pageQuery = PageableExecutionUtils.getPage(queryResults, pageable,
        () -> db.count(Query.of(query).limit(-1).skip(-1), clazz, getRepoName(clazz)));
        // return the query results
        queryResults = pageQuery.getContent();

        //APPROACH 2
        List<T> queryResults = db.find(query.allowDiskUse(true), DataModel.class, repoName);

        return queryResults;
    }

    @Override
    public boolean update(Map<String, String> params, Map<String, Object> data) {
        // generate query
        Query query = buildQuery(params);

        //This applies the same changes to every entry
        Update update = new Update();
        for (Map.Entry<String, Object> entry : data.entrySet()) {
            update.set(entry.getKey(), entry.getValue());
        }
        db.updateMulti(query, update, DataModel.class, repoName);

        return true;
    }

    private Query buildQuery(Map<String, String> params) {
        //...
    }
}