GAE Datastore Query Cursor Получение больших данных партиями - PullRequest
0 голосов
/ 08 марта 2019

Я пытаюсь получить более 1 миллиона сущностей в хранилище данных за один запрос, но с помощью пакетирования, чтобы избежать тайм-аута хранилища данных.

Вот мой код.

public List<T> listByLimitation(Query query, Integer limit)
        throws NoSuchMethodException, SecurityException, InstantiationException, IllegalAccessException,
        IllegalArgumentException, InvocationTargetException, Exception {
    Integer chunkSize = 100;
    Integer prefetchedSize = 100;
    if(limit >= 1000 && limit <= 5000)
    {
        chunkSize = 1000;
        prefetchedSize = 1000;
    }
    else if(limit >= 5001 && limit <= 10000)
    {
        chunkSize = 3000;
        prefetchedSize = 2000;
    }
    else if(limit >= 10001 && limit < 100000 )
    {
        chunkSize = 5000;
        prefetchedSize = 3000;
    }
    else
    {
        chunkSize = 7000;
        prefetchedSize = 5000;
    }


    List<T> models = Lists.newArrayListWithExpectedSize(200000);

    QueryResultList<Entity> queryResultList = datastore.prepare(query).asQueryResultList(FetchOptions.Builder.withLimit(limit).chunkSize(chunkSize).prefetchSize(prefetchedSize));
    Iterator<Entity> iterator = datastore.prepare(query).asIterator(FetchOptions.Builder.withLimit(limit).chunkSize(chunkSize).prefetchSize(prefetchedSize));
    while(true)
    {
        while (iterator.hasNext())
        {
            Constructor<T> constructor = cls.getConstructor(Entity.class);
            T model = constructor.newInstance(iterator.next());
            models.add(model);
        }
        this.logger.log(Level.SEVERE,"EntityModelSize:" + models.size()); //just for checking

        Cursor cursor = queryResultList.getCursor();

        queryResultList = datastore.prepare(query).asQueryResultList(FetchOptions.Builder.withLimit(limit).startCursor(cursor).chunkSize(chunkSize).prefetchSize(prefetchedSize));
        iterator = datastore.prepare(query).asIterator(FetchOptions.Builder.withLimit(limit).startCursor(cursor).chunkSize(chunkSize).prefetchSize(prefetchedSize));

        if(queryResultList.isEmpty())
        {
            break;
        }
    }



    return models;


}

и он возвращаетошибка.

java.lang.OutOfMemoryError: превышен лимит накладных расходов GC в свойстве com.google.storage.onestore.v3.OnestoreEntity $. (OnestoreEntity.java:4356) в com.google.storage.onestore.v3.OnestoreEntity $ EntityProto.addRawProperty (OnestoreEntity.java:9834) в com.google.storage.onestore.v3.OnestoreEntity $ EntityProto.merge (OnestoreEntity.java:10341) в com.google.apphosting.api.Datastore$ QueryResult.merge (DatastoreV3Pb.java:28421) на com.google.appengine.repackaged.com.google.io.protocol.ProtocolMessage.mergeFrom (ProtocolMessage.java:453) на com.google.appengine.repackaged.com.google..io.protocol.ProtocolMessage.mergeFrom (ProtocolMessage.java:470) на com.google.appengine.repackaged.com.google.io.protocol.ProtocolMessage.parseFrom (ProtocolMessage.java:579) на com.google.appengine.api.datastore.DatastoreApiHelper $ 1.wrap (DatastoreApiHelper.java:120) на com.google.appengine.api.datastore.DatastoreApiHelper $ 1.wrap (DatastoreApiHelper.java:113) на странице com.google.appengine.api.pper(FutureWrapper.java:60) на com.google.appengine.api.utils.FutureWrapper.get (FutureWrapper.java:101) на com.google.appengine.api.datastore.FutureHelper.getInternal (FutureHelper.java:69) наcom.google.appengine.api.datastore.FutureHelper.quietGet (FutureHelper.java:33) в com.google.appengine.api.datastore.BaseQueryResultsSource.loadMoreEntities (BaseQueryResultsSource.java:243) в com.googleiappengine.хранилище данныхjava: 99) в com.google.appengine.api.datastore.LazyList.getCursor (LazyList.java:325) в com.kustom360.lib.client.DatastoreController.listByLimitation (DatastoreController.java:132)

У меня есть задание потока данных для этого типа запроса, но я просто пытаюсь обработать получение больших данных, не используя какие-либо другие службы или API.

Я не думаю, что ошибка памяти не в моей стороне.Как указывает ошибка в методе getCursor их реализации LazyList.

Можно запросить миллионы объектов в пакетном режиме с помощью курсоров, но в одном запросе?

Спасибо!

...