0

Ich habe ndb Modelle:NDB Filtering für Strukturierte Immobilien Google App Engine

class Product(ndb.Model): 
    name = ndb.StringProperty() 
    description = ndb.StringProperty() 
    code = ndb.StringProperty() 

class Category(ndb.Model): 
    name = ndb.StringProperty() 

class Shop(ndb.Model): 
    name = ndb.StringProperty() 
    category = ndb.StructuredProperty(Category) 
    address = ndb.StringProperty() 

class ProductInShop(ndb.Model): 
    product = ndb.StructuredProperty(Product) 
    shop = ndb.StructuredProperty(Shop) 
    price = ndb.FloatProperty() 

Und in einer Funktion finde ich Artikel im Shop (Produktcode und Shop-Taste in Anfrage) benötigen. Wenn kein Produkt im Shop ist (Rückgabe keine), muss ich es erstellen. Wenn es vorhanden ist, aktualisieren Sie den Preiswert aus der Anfrage. Jetzt mache ich Abfrage von gql.

product_in_shop = ndb.gql(
     'SELECT * FROM ProductInShop WHERE \ 
product.code = :1 AND shop = :2 LIMIT 1', 
     request.code, 
     ndb.Key(Shop, request.shop_key).get() 
    ).get() 

Und es funktioniert gut. Aber! Einige Male product_in_shop = None wenn es eine Entität geben sollte (ich wurde in der Datenbank überprüft). Ich wurde versucht, eine weitere Abfrage zu machen, um Entitäten zu zählen, und es gibt 0 zurück, aber es gab mehr als 1 Entität.

Wenn ich diese Tasche sehen kann ich nur aktualisieren (Python appcfg.py -Ein Projekt-Name Update Projektname) und es funktioniert ...

Alle Ideen, was ich tue, falsch, oder wie es beheben?

+1

Ich denke, es ist mit Eventual Consistency verknüpft. https://cloud.google.com/datastore/docs/concepts/structuring_for_strong_consistency –

Antwort

1

Dies ist sehr wahrscheinlich Eventual Consistency. Wenn Sie Ihr System mit Cloud Datastore entwerfen, müssen Sie den Fall planen, dass diese Abfragen einige Zeit benötigen, um auf dem neuesten Stand zu sein. Wahrscheinlich dauert die erneute Bereitstellung Ihrer App in diesem Fall nur so lange, bis die Informationen zum Zeitpunkt der erneuten Überprüfung aktualisiert wurden.

Um eine starke Konsistenz zu gewährleisten, sollten Sie Ihre Daten in Entitätsgruppen organisieren. Eine wichtige Überlegung für Ihr Datenmodell ist, dass Sie innerhalb einer EG sehr konsistent abfragen können. Sie können jedoch nur eine einzelne Entitätsgruppe mit einer Rate von 1 Aktualisierung pro Sekunde aktualisieren (dieses Update kann jedoch eine Stapelaktualisierung sein).

Versuchen Sie, diese Entitätsgruppen entlang natürlicher Grenzen auszurichten, um die Rate zu verringern, mit der eine gegebene Entitätsgruppe bei der Skalierung Ihrer Anwendung geschrieben wird. Beispiel: Sie haben möglicherweise eine einzelne Entitätsgruppe pro Benutzer oder im Fall Ihrer Anwendung möglicherweise eine einzelne Entitätsgruppe pro Shop. Wenn Sie alle Product s für eine einzelne Shop in eine Entitätsgruppe einfügen, können Sie immer alle Product s in einem Shop auf konsistente Weise auflisten. Sie wären nicht in der Lage, die Anzahl der Personen, die Artikel zu einem Shop hinzufügen, zu erhöhen (Sie können nur Produkte pro Woche in einen Shop schreiben), aber dies wäre wahrscheinlich eine akzeptable Einschränkung für das System.

Berücksichtigung So folgendes Layout statt:

class Product(ndb.Model): 
    name = ndb.StringProperty() 
    description = ndb.StringProperty() 
    code = ndb.StringProperty() 

class Category(ndb.Model): 
    name = ndb.StringProperty() 

class Shop(ndb.Model): 
    name = ndb.StringProperty() 
    category = ndb.StructuredProperty(Category) 
    address = ndb.StringProperty() 

class ProductInShop(ndb.Model): 
    product = ndb.StructuredProperty(Product) 
    price = ndb.FloatProperty() 

Wenn Sie eine ProductInShop erstellen, Sie werden die Eltern auf den Schlüssel des Shop, dass es ein Teil festlegen möchten. Zum Beispiel:

ProductInShop(parent=ndb.Key(Shop, request.shop_key), 
    product=Product(...), price=10.0).put() 

Dann können Sie Ihre Anfrage nach einem Produkt in einem bestimmten Geschäft mit einem bestimmten Code ausgeben:

product_in_shop = ndb.gql(
     'SELECT * FROM ProductInShop WHERE \ 
product.code = :1 AND ANCESTOR IS :2 LIMIT 1', 
     request.code, 
     ndb.Key(Shop, request.shop_key) 
    ).get() 

Als Randnotiz, wenn Ihre code einzigartig zu einem einzigen Produkt, Berücksichtigen Sie beim Festlegen der ID ProductInShop den Code.Dann müssen Sie nicht eine Abfrage für dieses Problem:

ProductInShop(id=product.code, product=product, price=10.0).put() 

Dann können Sie Ihre ProductInShop Nachschlag ohne eine Abfrage mit zur Ausgabe mit:

product_in_shop = ndb.Key(Shop, request.shop_key, ProductInShop, request.code).get()