Beispiel #1
0
 def test_serialize_a_promotion(self):
     """ Test serialization of a Promotion"""
     promotion = Promotion(
         name="New_Sale",
         description="Amazing",
         start_date=datetime.strptime('2001-01-01 00:00:00',
                                      '%Y-%m-%d %H:%M:%S'),
         end_date=datetime.strptime('2001-01-01 00:00:00',
                                    '%Y-%m-%d %H:%M:%S'))
     data = promotion.serialize()
     self.assertNotEqual(data, None)
     self.assertIn("id", data)
     self.assertEqual(data["id"], None)
     self.assertIn("name", data)
     self.assertEqual(data["name"], "New_Sale")
     self.assertIn("description", data)
     self.assertEqual(data["description"], "Amazing")
     self.assertIn("start_date", data)
     self.assertEqual(
         datetime.strptime(data["start_date"], DATETIME_FORMAT),
         datetime.strptime('2001-01-01 00:00:00', DATETIME_FORMAT))
     self.assertIn("end_date", data)
     self.assertEqual(
         datetime.strptime(data["end_date"], DATETIME_FORMAT),
         datetime.strptime('2001-01-01 00:00:00', DATETIME_FORMAT))
Beispiel #2
0
    def get(self):
        """ Returns all of the Promotions """
        app.logger.info('Request to list Promotions...')
        promotions = []
        category = request.args.get('category')
        productid = request.args.get('productid')
        available = request.args.get('available')
        discount = request.args.get('discount')
        if category:
            app.logger.info('Filtering by category: %s', category)
            promotions = Promotion.find_by_category(category)
        elif productid:
            app.logger.info('Filtering by productid:%s', productid)
            promotions = Promotion.find_by_productid(productid)
        elif available:
            app.logger.info('Filtering by available: %s', available)
            is_available = available.lower() in ['yes', 'y', 'true', 't', '1']
            promotions = Promotion.find_by_availability(is_available)
        elif discount:
            app.logger.info('Filtering by discount:%s', discount)
            promotions = Promotion.find_by_discount(discount)
        else:
            promotions = Promotion.all()

        app.logger.info('[%s] Promotions returned', len(promotions))
        results = [promotion.serialize() for promotion in promotions]
        return results, status.HTTP_200_OK
Beispiel #3
0
 def test_find_by_availability(self):
     """ Find a Promotion by Availability """
     Promotion("A002", "dog", False).save()
     Promotion("kitty", "cat", True).save()
     promotions = Promotion.find_by_availability(True)
     self.assertEqual(len(promotions), 1)
     self.assertEqual(promotions[0].productid, "kitty")
Beispiel #4
0
 def test_serialize(self):
     """ Test serialization of a Promotion """
     promotion = Promotion(
         id=1,
         title="Halloween Special",
         description="Some items off in honor of the spookiest month.",
         promo_code="hween",
         promo_type=PromoType.DISCOUNT,
         amount=25,
         start_date=datetime(2020, 10, 20),
         end_date=datetime(2020, 11, 1),
         is_site_wide=True,
     )
     product_1 = Product()
     product_1.id = 123
     promotion.products.append(product_1)
     product_2 = Product()
     product_2.id = 456
     promotion.products.append(product_2)
     self.assertEqual(
         promotion.serialize(),
         {
             "id": 1,
             "title": "Halloween Special",
             "description":
             "Some items off in honor of the spookiest month.",
             "promo_code": "hween",
             "promo_type": "DISCOUNT",
             "amount": 25,
             "start_date": "2020-10-20T00:00:00",
             "end_date": "2020-11-01T00:00:00",
             "is_site_wide": True,
             "products": [123, 456],
         },
     )
Beispiel #5
0
 def setUpClass(cls):
     """ This runs once before the entire test suite """
     app.config['TESTING'] = True
     app.config['DEBUG'] = False
     app.config["SQLALCHEMY_DATABASE_URI"] = DATABASE_URI
     app.logger.setLevel(logging.CRITICAL)
     Promotion.init_db(app)
     pass
Beispiel #6
0
 def test_find_by_category(self):
     """ Find a Promotion by Category """
     Promotion("A002", "dog").save()
     Promotion("kitty", "cat").save()
     promotions = Promotion.find_by_category("cat")
     self.assertNotEqual(len(promotions), 0)
     self.assertEqual(promotions[0].category, "cat")
     self.assertEqual(promotions[0].productid, "kitty")
 def test_update_promotion(self):
     """ Update a promotion """
     promotion = PromotionFactory()
     promotion.save()
     self.assertEqual(len(Promotion.find_by_code(promotion.code)), 1)
     promotion.percentage = 80
     promotion.start_date = promotion.start_date+1000
     promotion.expiry_date = promotion.expiry_date+1000
     promotion.save()
     self.assertEqual(len(Promotion.find_by_code(promotion.code)), 1)
Beispiel #8
0
 def setUpClass(cls):
     """ This runs once before the entire test suite """
     global DATABASE_URI
     app.config['TESTING'] = True
     app.config['DEBUG'] = False
     if 'VCAP_SERVICES' in os.environ:
         vcap = json.loads(os.environ['VCAP_SERVICES'])
         DATABASE_URI = vcap['user-provided'][0]['credentials']['url']
     app.config["SQLALCHEMY_DATABASE_URI"] = DATABASE_URI
     app.logger.setLevel(logging.CRITICAL)
     Promotion.init_db(app)
Beispiel #9
0
 def test_deserialize_a_promotion(self):
     """ Deserialize a Promotion """
     data = {"productid": "A002", "category": "BOGO", "available": True, "discount": 10 }
     promotion = Promotion()
     promotion.deserialize(data)
     self.assertNotEqual(promotion, None)
     #self.assertEqual(promotion.id, None)
     self.assertEqual(promotion.productid, "A002")
     self.assertEqual(promotion.category, "BOGO")
     self.assertEqual(promotion.available, True)
     self.assertEqual(promotion.discount, 10)
Beispiel #10
0
 def test_serialize_a_promotion(self):
     """ Serialize a Promotion """
     promotion = Promotion("A002", "dog", False)
     data = promotion.serialize()
     self.assertNotEqual(data, None)
     self.assertNotIn('_id', data)
     self.assertIn('productid', data)
     self.assertEqual(data['productid'], "A002")
     self.assertIn('category', data)
     self.assertEqual(data['category'], "dog")
     self.assertIn('available', data)
     self.assertEqual(data['available'], False)
Beispiel #11
0
def list_promotions():
    """ Returns all of the Promotions """
    app.logger.info("Request for promotions list")
    promotions = []
    name = request.args.get("name")
    if name:
        promotions = Promotion.find_by_name(name)
    else:
        promotions = Promotion.all()

    results = [promotion.serialize() for promotion in promotions]
    return make_response(jsonify(results), status.HTTP_200_OK)
    def test_find_by_code(self):
        """ Find Promotions by code """
        self.assertEqual(len(Promotion.all()), 0)
        codes = ['SAVE15', 'SAVE20', 'SAVE30']
        counts = [10, 15, 2]
        for count, code in zip(counts, codes):
            PromotionFactory.batch_create(count, code=code)

        for count, code in zip(counts, codes):
            promotions = Promotion.find_by_code(code)
            self.assertEqual(len(promotions), count)
            for promotion in promotions:
                self.assertEqual(promotion.code, code)
Beispiel #13
0
 def test_update_a_promotion_fail(self):
     promotion = Promotion(
         title="test_create",
         promo_type=PromoType.DISCOUNT,
         amount=10,
         start_date=datetime(2020, 10, 17),
         end_date=datetime(2020, 10, 18),
         is_site_wide=True,
     )
     try:
         promotion.update()
     except:
         print("Update called with empty ID field")
    def test_promotion_deserialize_exceptions(self):
        """ Test Promotion deserialization exceptions"""
        promotion = PromotionFactory()
        json_data = json.dumps(dict(
            percentage=promotion.percentage,
            start_date=promotion.start_date,
        ))
        promotion_deserialized = Promotion()
        try:
            promotion_deserialized.deserialize(json.loads(json_data))
        except DataValidationError:
            self.assertRaises(DataValidationError)

        json_data = json.dumps(dict(
            code=promotion.code,
            percentage=promotion.percentage,
            expiry_date="shouldn't like this",
            start_date=promotion.start_date,
            products=promotion.products
        ))
        promotion_deserialized = Promotion()
        try:
            promotion_deserialized.deserialize(json.loads(json_data))
        except DataValidationError:
            self.assertRaises(DataValidationError)
Beispiel #15
0
 def test_delete_a_promotion(self):
     """ Delete a Promotion """
     promotion = Promotion("A002", "dog")
     promotion.save()
     self.assertEqual(len(Promotion.all()), 1)
     # delete the promotion and make sure it isn't in the database
     promotion.delete()
     self.assertEqual(len(Promotion.all()), 0)
Beispiel #16
0
 def test_find_promotion(self):
     """ Find a Promotion by ID """
     promotions = PromotionFactory.create_batch(3)
     for promotion in promotions:
         promotion.create()
     logging.debug(promotions)
     # make sure they got saved
     self.assertEqual(len(Promotion.all()), 3)
     # find the 2nd promotion in the list
     promotion = Promotion.find(promotions[1].id)
     self.assertIsNot(promotion, None)
     self.assertEqual(promotion.id, promotions[1].id)
     self.assertEqual(promotion.name, promotions[1].name)
     self.assertEqual(promotion.description, promotions[1].description)
     self.assertEqual(promotion.end_date, promotions[1].end_date)
     self.assertEqual(promotion.start_date, promotions[1].start_date)
    def post(self, promotion_id):
        """
        Apply a promotion on a given set of products together with their prices

        This endpoint will return those given products with their updated price.
        Products that are not eligible to the given promotion will be returned without any update
        """
        app.logger.info('Apply promotion {%s} to products', promotion_id)
        check_content_type('application/json')
        data = request.get_json()

        # Get promotion data
        promotion = Promotion.find(promotion_id)
        if not promotion:
            api.abort(
                status.HTTP_404_NOT_FOUND,
                'Promotion with id "{}" was not found.'.format(promotion_id))

        # Check promotion availability
        if not promotion.is_active():
            api.abort(
                status.HTTP_409_CONFLICT,
                'Promotion with id "{}" is not active.'.format(promotion_id))

        # Get product data
        try:
            products = data['products']
            assert isinstance(products, list)
        except KeyError:
            raise DataValidationError('Missing products key in request data')
        except AssertionError:
            raise DataValidationError('The given products in request data \
                should be a list of serialized product objects')

        # Apply promotion on products
        products_with_new_prices = []
        eligible_ids = promotion.products
        non_eligible_ids = []
        print(eligible_ids)
        for product in products:
            product_id = product['product_id']
            try:
                new_price = float(product['price'])
            except ValueError:
                raise DataValidationError(
                    'The given product prices cannot convert to a float number'
                )
            if product_id in eligible_ids:
                new_price = new_price * (promotion.percentage / 100.0)
            else:
                non_eligible_ids.append(product_id)
            product['price'] = new_price
            products_with_new_prices.append(product)

        if len(non_eligible_ids) > 0:
            app.logger.info(
                'The following products are not \
                eligible to the given promotion: %s', non_eligible_ids)

        return {"products": products_with_new_prices}, status.HTTP_200_OK
 def test_add_a_promotion(self):
     """ Create a promotion """
     promotion = PromotionFactory(code="SAVE50")
     promotion.save()
     promotions = Promotion.all()
     self.assertEqual(len(promotions), 1)
     self.assertEqual(promotions[0].code, "SAVE50")
Beispiel #19
0
 def test_key_error_on_update(self, bad_mock):
     """ Test KeyError on update """
     bad_mock.side_effect = KeyError()
     promotion = Promotion("A002", "dog", False)
     promotion.save()
     promotion.productid = 'Fifi'
     promotion.update()
Beispiel #20
0
 def test_create_a_promotion(self):
     """ Create a promotion and assert that it exists """
     promotion = Promotion("A002", "BOGO", True, 10)
     self.assertNotEqual(promotion, None)
     #self.assertEqual(promotion.id, None)
     self.assertEqual(promotion.productid, "A002")
     self.assertEqual(promotion.category, "BOGO")
     self.assertEqual(promotion.available, True)
     self.assertEqual(promotion.discount, 10)
 def setUp(self):
     """ Initialize the Cloudant database """
     self.app = app.test_client()
     Promotion.init_db("tests")
     Promotion.remove_all()
     Promotion("A001", "BOGO", True, 10).save()
     Promotion("A002", "B2GO", True, 10).save()
     Promotion("A003", "B3GO", False, 10).save()
def read_promotions(promotion_id):
    """
    Reads a single promotion
    This endpoint will read an promotion based on it's promotion id
    """
    app.logger.info("Request to read an promotion with id: {}".format(promotion_id))
    promotion = Promotion.find(promotion_id)
    if not promotion:
        raise NotFound("promotion with id '{}' was not found.".format(promotion_id))
    return make_response(jsonify(promotion.serialize()), status.HTTP_200_OK)
Beispiel #23
0
def delete_promotion(promotion_id):
    """
    Delete a Promotion
    This endpoint will delete a Promotion based the id specified in the path
    """
    app.logger.info("Request to delete promotion with id: %s", promotion_id)
    promotion = Promotion.find(promotion_id)
    if promotion:
        promotion.delete()
    return make_response("", status.HTTP_204_NO_CONTENT)
 def test_promotion_deserialize(self):
     """ Test Promotion deserialization"""
     promotion = PromotionFactory()
     json_data = json.dumps(dict(
         code=promotion.code,
         percentage=promotion.percentage,
         expiry_date=promotion.expiry_date,
         start_date=promotion.start_date,
         products=promotion.products
     ))
     promotion_deserialized = Promotion()
     promotion_deserialized.deserialize(json.loads(json_data))
     self.assertEqual(promotion.code, promotion_deserialized.code)
     self.assertEqual(promotion.percentage,
                      promotion_deserialized.percentage)
     self.assertEqual(promotion.expiry_date,
                      promotion_deserialized.expiry_date)
     self.assertEqual(promotion.start_date,
                      promotion_deserialized.start_date)
Beispiel #25
0
def get_promotions(promotion_id):
    """
    Retrieve a single Promotion
    This endpoint will return a Promotion based on it's id
    """
    app.logger.info("Request for promotion with id: %s", promotion_id)
    promotion = Promotion.find(promotion_id)
    if not promotion:
        raise NotFound(
            "Promotion with id '{}' was not found.".format(promotion_id))
    return make_response(jsonify(promotion.serialize()), status.HTTP_200_OK)
    def test_find(self):
        """ Find a Promotion by ID """
        PromotionFactory(code="SAVE30").save()
        save50 = PromotionFactory(code="SAVE50")
        save50.save()

        promotion = Promotion.find(save50.id)
        self.assertIsNot(promotion, None)
        self.assertEqual(promotion.id, save50.id)
        self.assertEqual(promotion.code, save50.code)
        self.assertEqual(promotion.percentage, save50.percentage)
    def delete(self, promotion_id):
        """
        Delete a Promotion

        This endpoint will delete a Promotion based the id specified in the path
        """
        app.logger.info('Request to Delete a promotion with id [%s]',
                        promotion_id)
        promotion = Promotion.find(promotion_id)
        if promotion:
            promotion.delete()
        return '', status.HTTP_204_NO_CONTENT
Beispiel #28
0
 def test_deserialize_a_promotion(self):
     """ Test deserialization of a promotion """
     promotion = Promotion(
         name="New_Sale",
         description="Amazing",
         start_date=datetime.strptime('2001-01-01 00:00:00',
                                      '%Y-%m-%d %H:%M:%S'),
         end_date=datetime.strptime('2001-01-01 00:00:00',
                                    '%Y-%m-%d %H:%M:%S'))
     data = promotion.serialize()
     promotion.deserialize(data)
     self.assertNotEqual(promotion, None)
     self.assertEqual(promotion.id, None)
     self.assertEqual(promotion.name, "New_Sale")
     self.assertEqual(promotion.description, "Amazing")
     self.assertEqual(
         promotion.start_date,
         datetime.strptime('2001-01-01 00:00:00', DATETIME_FORMAT))
     self.assertEqual(
         promotion.end_date,
         datetime.strptime('2001-01-01 00:00:00', DATETIME_FORMAT))
Beispiel #29
0
 def test_update_a_promotion(self):
     """ Update a Promotion """
     promotion = Promotion("A002", "dog", True)
     promotion.save()
     self.assertNotEqual(promotion.id, None)
     # Change it an save it
     promotion.category = "k9"
     promotion.save()
     # Fetch it back and make sure the id hasn't changed
     # but the data did change
     promotions = Promotion.all()
     self.assertEqual(len(promotions), 1)
     self.assertEqual(promotions[0].category, "k9")
     self.assertEqual(promotions[0].productid, "A002")
Beispiel #30
0
 def test_delete_a_promotion(self):
     """ Delete a Promotion """
     promotion = Promotion(
         name="Default",
         description="default description",
         start_date=datetime.strptime('2001-01-01 00:00:00',
                                      '%Y-%d-%m %H:%M:%S'),
         end_date=datetime.strptime('2001-01-01 00:00:00',
                                    '%Y-%d-%m %H:%M:%S'))
     promotion.create()
     self.assertEqual(len(Promotion.all()), 1)
     # delete the promotion and make sure it isn't in the database
     promotion.delete()
     self.assertEqual(len(Promotion.all()), 0)