def testUpdateAverageRatingNonBatch2(self):
    "Check the number of tasks added to the queue when reviews are created."

    models.Category.buildAllCategories()
    product = docs.Product.buildProduct(PRODUCT_PARAMS)
    config.BATCH_RATINGS_UPDATE = False

    # Create a review object and invoke updateAverageRating.
    review = models.Review(product_key=product.key,
                           username='******',
                           rating=4,
                           comment='comment'
                           )
    review.put()
    utils.updateAverageRating(review.key)
    review = models.Review(product_key=product.key,
                           username='******',
                           rating=1,
                           comment='comment'
                           )
    review.put()
    utils.updateAverageRating(review.key)

    # Check the number of tasks in the queue
    taskq = self.testbed.get_stub(testbed.TASKQUEUE_SERVICE_NAME)
    tasks = taskq.GetTasks("default")
    taskq.FlushQueue("default")
    self.assertEqual(len(tasks), 2)
  def testUpdateAverageRatingBatch(self):
    "Test batch mode avg ratings updating."
    models.Category.buildAllCategories()
    product = docs.Product.buildProduct(PRODUCT_PARAMS)
    config.BATCH_RATINGS_UPDATE = True

    # Create a review object and invoke updateAverageRating.
    review = models.Review(product_key=product.key,
                           username='******',
                           rating=5,
                           comment='comment'
                           )
    review.put()
    utils.updateAverageRating(review.key)

    # there should not be any task queue tasks
    taskq = self.testbed.get_stub(testbed.TASKQUEUE_SERVICE_NAME)
    tasks = taskq.GetTasks("default")
    taskq.FlushQueue("default")
    self.assertEqual(len(tasks), 0)

    # with BATCH_RATINGS_UPDATE = True, the product document's average rating
    # field ('ar') should not yet be updated to match its associated product
    # entity.
    product = models.Product.get_by_id(product.pid)
    sq = search.Query(query_string='ar:5.0')
    res = docs.Product.getIndex().search(sq)
    self.assertEqual(res.number_found, 0)
  def testUpdateAverageRatingNonBatch1(self):
    "Test non-batch mode avg ratings updating."
    models.Category.buildAllCategories()
    product = docs.Product.buildProduct(PRODUCT_PARAMS)
    self.assertEqual(product.avg_rating, 0)
    config.BATCH_RATINGS_UPDATE = False

    # Create a review object and invoke updateAverageRating.
    review = models.Review(product_key=product.key,
                           username='******',
                           rating=4,
                           comment='comment'
                           )
    review.put()
    utils.updateAverageRating(review.key)
    review = models.Review(product_key=product.key,
                           username='******',
                           rating=1,
                           comment='comment'
                           )
    review.put()
    utils.updateAverageRating(review.key)

    product = models.Product.get_by_id(product.pid)
    # check that the parent product rating average has been updated based on the
    # two reviews
    self.assertEqual(product.avg_rating, 2.5)
    # with BATCH_RATINGS_UPDATE = False, the product document's average rating
    # field ('ar') should be updated to match its associated product
    # entity.

    # run the task queue tasks
    taskq = self.testbed.get_stub(testbed.TASKQUEUE_SERVICE_NAME)
    tasks = taskq.GetTasks("default")
    taskq.FlushQueue("default")
    while tasks:
      for task in tasks:
        deferred.run(base64.b64decode(task["body"]))
      tasks = taskq.GetTasks("default")
      taskq.FlushQueue("default")

    sq = search.Query(query_string='ar:2.5')
    res = docs.Product.getIndex().search(sq)
    self.assertEqual(res.number_found, 1)
    for doc in res:
      self.assertEqual(doc.doc_id, product.doc_id)