Хранилище данных иногда не может получить все необходимые объекты, но работает во второй раз

У меня есть объект хранилища данных под названием lineItems, который состоит из отдельных позиций, по которым должен быть выставлен счет. Пользователи находят позиции и прикрепляют к ним номер заказа на покупку. Они отображаются на веб-странице, где они могут создать счет-фактуру.

Я бы показал свой код для извлечения сущностей, но я не думаю, что это вообще имеет значение, так как это тоже происходило пару раз, когда я использовал управляемую виртуальную машину несколько месяцев назад, и код был совершенно другим. (Раньше я использовал objectify, теперь использую API хранилища данных). Вкратце, в настоящее время я просто использую StructuredQuery.setFilter (новый PropertyFilter.eq ("POnum", ponum)). SetFilter (new PropertyFilter.eq ("Invoiced", false)); (это псевдокод, вы не можете использовать два таких .setFilter. Настоящий код принимает список PropertyFilters и правильно создает составной фильтр.)

Этим утром произошло то, что администратор создал счет, и все, кроме двух строк, были в счете. Было две строки, которые код так и не получил, и эти строки застряли в разделе «счета для создания».

Администратор просто снова создал счет-фактуру для данного номера заказа на покупку, но во второй раз он ДЕЙСТВИТЕЛЬНО взял две оставшиеся строки и создал второй счет-фактуру.

Обратите внимание, что сущности были созданы / отредактированы почти 24 часа назад (когда она присвоила им номер заказа на поставку), поэтому они довольно долго сидели в базе данных. (Я проверил свои логи). Это не тот случай, когда они были только что созданы, а затем к ним попытались получить доступ в течение короткого периода времени. Это также НЕ случай неудачного обновления сущностей - код создает счет в стороннем бухгалтерском пакете, а их там просто не было. После успешного создания счета все объекты обновляются с помощью invoiced = true и записываются в хранилище данных. Таким образом, строки, которых не было в счете-фактуре в бухгалтерской программе, не были обновлены в хранилище данных. (Это тоже не «умная» проверка, она не проверяет построчно. Она просто проверяет, было ли создание счета-фактуры успешным или нет, а затем обновляет все сущности, которые у него есть в памяти).

Насколько я могу судить, хранилище данных просто не вернуло все объекты, которые соответствовали запросу в первый раз, но вернуло во второй раз.

Существует около 40 000 сущностей lineItem.

При каких условиях выборка из хранилища данных может случайно не захватить все объекты, которые соответствуют параметрам поиска StructuredQuery? (Обратите внимание, что это также произошло дважды при использовании Objectify на устаревшей управляемой архитектуре виртуальных машин.) Как я могу предотвратить это или проверить, произошло ли это?


comment
С Objectify вы, вероятно, брали все из Memcache, и это не беспокоило w / Datastore. Если вы не используете отношения родитель / ребенок для поиска вещей, тогда это будет сложно. Вы также должны посмотреть на денормализацию данных, где это возможно.   -  person Les Vogel - Google DevRel    schedule 29.07.2017
comment
Я не использовал memcache ... и у меня та же проблема с новым кодом, использующим гибкий API хранилища данных движка приложений. Это был простой поиск, верните список, в котором PurchaseOrder = 123456. Код запускался один раз и улавливал 8/10 сущностей. Затем пользователь запустил его снова, и он взял последние два ... Сущности были обновлены за 24 часа до этого, а также были доступны прямо перед этим должным образом. Кажется, это случай одного случайного неверного считывания из 3. (Один для отображения данных на странице, один во время их обработки и последний, когда пользователь повторно обработал данные).   -  person KevinG    schedule 29.07.2017
comment
Я не уверен, каковы будут преимущества отношений родитель / потомок ... Если у меня есть поле в моем объекте с именемpurchaseOrderNumber, invoiceNumber и т. Д., Я хотел бы просто упростить и просто искать все сущности для PurchaseOrderNumber. (На самом деле это намного сложнее, чем это, номера заказов на поставку, номера заказов на работу, авторизованные, место, дату работы ... Это сочетание всех этих полей, совпадающих, что определяет, что происходит в каждом счете-фактуре. После создания счета-фактуры , Я мог видеть использование отношений родитель / потомок, поскольку у каждого объекта будет только один родитель ...)   -  person KevinG    schedule 29.07.2017


Ответы (1)


Вы можете увидеть возможную согласованность, потому что вы не используете запрос предка.

См. https://cloud.google.com/datastore/docs/articles/balancing-strong-and-eventual-consistency-with-google-cloud-datastore/

person Joshua Melcon    schedule 27.07.2017
comment
Я не верю, что это так. Последний раз объект обновлялся 26 июля. 27 июля в 8:08 запрос был выполнен, и в нем пропущены 2 объекта. Примерно через 30 секунд пользователь снова выполнил запрос, только на этот раз он выбрал две сущности, которые пропустил в первый раз ... Кроме того, чтобы отобразить данные в первую очередь в разделе счетов-фактур для создания, используется тот же код. используется для получения сущностей. Итак, это сработало для отображения, не удалось получить их снова с сервера, а затем сработала третья выборка. - person KevinG; 28.07.2017