예제 #1
0
def test_add_variation_product_to_basket(admin_user, settings):
    configure(settings)
    shop = factories.get_default_shop()
    basket = factories.get_basket()
    factories.get_default_payment_method()
    factories.get_default_shipping_method()

    parent = factories.create_product("ComplexVarParent", shop=shop, supplier=factories.get_default_supplier())
    sizes = [("%sL" % ("X" * x)) for x in range(4)]
    for size in sizes:
        child = factories.create_product("ComplexVarChild-%s" % size, shop=shop, supplier=factories.get_default_supplier())
        child.link_to_parent(parent, variables={"size": size})

    parent_shop_product = parent.get_shop_instance(shop)
    parent_shop_product.refresh_from_db()

    client = _get_client(admin_user)

    # add parent shop product
    payload = {
        'shop_product': parent_shop_product.id
    }
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_400_BAD_REQUEST

    # add children shop product
    children_shop_product = parent_shop_product.product.variation_children.first().get_shop_instance(shop)
    payload = {
        'shop_product': children_shop_product.pk,
    }
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_200_OK
    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1
    assert not response_data["validation_errors"]
예제 #2
0
def test_update_line_quantity(admin_user, settings):
    configure(settings)
    shop = factories.get_default_shop()
    basket = factories.get_basket()
    factories.get_default_payment_method()
    factories.get_default_shipping_method()
    shop_product = factories.get_default_shop_product()
    shop_product.default_price = TaxfulPrice(1, shop.currency)
    shop_product.save()
    client = _get_client(admin_user)
    # add shop product
    payload = {
        'shop_product': shop_product.id
    }
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_200_OK

    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1

    payload = {
        "line_id": response_data["items"][0]["line_id"],
        "quantity": 5
    }
    response = client.post('/api/shuup/basket/{}-{}/update_quantity/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_200_OK

    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1
    assert response_data["items"][0]["shop_product"] == shop_product.pk
    assert float(response_data["items"][0]["quantity"]) == 5
    assert float(response_data["total_price"]) == 5
    basket.refresh_from_db()
    assert Basket.objects.first().data["lines"][0]["quantity"] == 5
예제 #3
0
def test_add_product_to_basket(admin_user, settings):
    configure(settings)
    shop = factories.get_default_shop()
    basket = factories.get_basket()
    factories.get_default_payment_method()
    factories.get_default_shipping_method()
    shop_product = factories.get_default_shop_product()
    shop_product.default_price = TaxfulPrice(1, shop.currency)
    shop_product.save()
    client = _get_client(admin_user)
    # add shop product
    payload = {
        'shop_product': shop_product.id
    }
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_200_OK

    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1
    assert response_data["items"][0]["shop_product"] == shop_product.pk
    assert not response_data["validation_errors"]
    assert float(response_data["total_price"]) == 1

    # add product
    payload = {
        'product': shop_product.product.pk,
        'shop': shop.pk
    }
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_200_OK
    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1
    assert not response_data["validation_errors"]
    assert float(response_data["total_price"]) == 2
예제 #4
0
def test_set_shipping_address(admin_user):
    shop = factories.get_default_shop()
    basket = factories.get_basket()
    factories.get_default_payment_method()
    factories.get_default_shipping_method()
    client = _get_client(admin_user)
    addr1 = factories.get_address()
    addr1.save()

    # use existing address
    payload = {
        'id': addr1.id
    }
    response = client.post('/api/shuup/basket/{}-{}/set_shipping_address/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_200_OK
    response_data = json.loads(response.content.decode("utf-8"))
    shipping_addr = response_data["shipping_address"]
    assert shipping_addr["id"] == addr1.id
    assert shipping_addr["prefix"] == addr1.prefix
    assert shipping_addr["name"] == addr1.name
    assert shipping_addr["postal_code"] == addr1.postal_code
    assert shipping_addr["street"] == addr1.street
    assert shipping_addr["city"] == addr1.city
    assert shipping_addr["country"] == addr1.country

    # create a new address
    address_data = {
        'name': 'name',
        'prefix': 'prefix',
        'postal_code': 'postal_code',
        'street': 'street',
        'city': 'city',
        'country': 'BR'
    }
    response = client.post('/api/shuup/basket/{}-{}/set_shipping_address/'.format(shop.pk, basket.key), address_data)
    assert response.status_code == status.HTTP_200_OK
    response_data = json.loads(response.content.decode("utf-8"))
    shipping_addr = response_data["shipping_address"]
    assert shipping_addr["id"] == addr1.id+1
    assert shipping_addr["prefix"] == address_data["prefix"]
    assert shipping_addr["name"] == address_data["name"]
    assert shipping_addr["postal_code"] == address_data["postal_code"]
    assert shipping_addr["street"] == address_data["street"]
    assert shipping_addr["city"] == address_data["city"]
    assert shipping_addr["country"] == address_data["country"]

    # get the basket and check the address
    response = client.get('/api/shuup/basket/{}-{}/'.format(shop.pk, basket.key))
    assert response.status_code == status.HTTP_200_OK
    response_data = json.loads(response.content.decode("utf-8"))
    shipping_addr = response_data["shipping_address"]
    assert shipping_addr["id"] == addr1.id+1
    assert shipping_addr["prefix"] == address_data["prefix"]
    assert shipping_addr["name"] == address_data["name"]
    assert shipping_addr["postal_code"] == address_data["postal_code"]
    assert shipping_addr["street"] == address_data["street"]
    assert shipping_addr["city"] == address_data["city"]
    assert shipping_addr["country"] == address_data["country"]
예제 #5
0
def seed_source(user):
    source = BasketishOrderSource(get_default_shop())
    billing_address = get_address()
    shipping_address = get_address(name="Shippy Doge")
    source.status = get_initial_order_status()
    source.billing_address = billing_address
    source.shipping_address = shipping_address
    source.customer = get_person_contact(user)
    source.payment_method = get_default_payment_method()
    source.shipping_method = get_default_shipping_method()
    assert source.payment_method_id == get_default_payment_method().id
    assert source.shipping_method_id == get_default_shipping_method().id
    return source
예제 #6
0
def test_create_order(admin_user, settings, target_customer):
    configure(settings)
    shop = factories.get_default_shop()
    basket = factories.get_basket()
    factories.create_default_order_statuses()
    shop_product = factories.get_default_shop_product()
    shop_product.default_price = TaxfulPrice(1, shop.currency)
    shop_product.save()
    client = _get_client(admin_user)
    # add shop product
    payload = {
        'shop_product': shop_product.id
    }

    if target_customer == "other":
        target = factories.create_random_person()
        payload["customer_id"] = target.pk
    else:
        target = get_person_contact(admin_user)


    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_200_OK

    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1
    response = client.post('/api/shuup/basket/{}-{}/create_order/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_400_BAD_REQUEST
    response_data = json.loads(response.content.decode("utf-8"))
    assert "errors" in response_data

    factories.get_default_payment_method()
    factories.get_default_shipping_method()
    response = client.post('/api/shuup/basket/{}-{}/create_order/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_201_CREATED
    response_data = json.loads(response.content.decode("utf-8"))
    basket.refresh_from_db()
    assert basket.finished
    order = Order.objects.get(reference_number=response_data["reference_number"])
    assert order.status == OrderStatus.objects.get_default_initial()
    assert order.payment_status == PaymentStatus.NOT_PAID
    assert order.shipping_status == ShippingStatus.NOT_SHIPPED
    assert not order.payment_method
    assert not order.shipping_method
    assert float(order.taxful_total_price_value) == 1
    assert order.customer == target
    assert order.orderer == get_person_contact(admin_user)
    assert order.creator == admin_user
    assert not order.billing_address
    assert not order.shipping_address
예제 #7
0
def test_abandoned_baskets(admin_user, settings):
    configure(settings)
    shop = factories.get_default_shop()
    factories.get_default_payment_method()
    factories.get_default_shipping_method()

    basket1 = factories.get_basket()

    shop_product = factories.get_default_shop_product()
    shop_product.default_price = TaxfulPrice(1, shop.currency)
    shop_product.save()
    client = _get_client(admin_user)
    # add shop product
    payload = {'shop_product': shop_product.id}
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket1.key), payload)
    assert response.status_code == status.HTTP_200_OK
    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1
    assert response_data["items"][0]["shop_product"] == shop_product.pk
    assert not response_data["validation_errors"]
    assert float(response_data["total_price"]) == 1
    assert Basket.objects.count() == 1

    response = client.get("/api/shuup/basket/abandoned/?shop={}&days_ago=0&not_updated_in_hours=0".format(shop.pk))
    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data) == 1
    basket_data = response_data[0]
    assert basket_data["id"] == basket1.id


    basket2 = factories.get_basket()
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket2.key), payload)
    assert response.status_code == status.HTTP_200_OK
    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1
    assert response_data["items"][0]["shop_product"] == shop_product.pk
    assert not response_data["validation_errors"]
    assert float(response_data["total_price"]) == 1
    assert Basket.objects.count() == 2

    response = client.get("/api/shuup/basket/abandoned/?shop={}&days_ago=0&not_updated_in_hours=0".format(shop.pk))
    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data) == 2
    basket_data = response_data[1]
    assert basket_data["id"] == basket2.id

    # there is no shop with this id thus it should return 404
    response = client.get("/api/shuup/basket/abandoned/?shop=2&days_ago=0&not_updated_in_hours=0")
    assert response.status_code == status.HTTP_404_NOT_FOUND
예제 #8
0
def test_basket(rf, storage):
    StoredBasket.objects.all().delete()
    quantities = [3, 12, 44, 23, 65]
    shop = get_default_shop()
    get_default_payment_method()  # Can't create baskets without payment methods
    supplier = get_default_supplier()
    products_and_quantities = []
    for quantity in quantities:
        product = create_product(printable_gibberish(), shop=shop, supplier=supplier, default_price=50)
        products_and_quantities.append((product, quantity))

    is_database = (storage == "shuup.front.basket.storage:DatabaseBasketStorage")
    with override_settings(SHUUP_BASKET_STORAGE_CLASS_SPEC=storage):
        for product, q in products_and_quantities:
            request = rf.get("/")
            request.session = {}
            request.shop = shop
            apply_request_middleware(request)
            basket = get_basket(request)
            assert basket == request.basket
            assert basket.product_count == 0
            line = basket.add_product(supplier=supplier, shop=shop, product=product, quantity=q)
            basket.shipping_method = get_shipping_method(shop=shop)  # For shippable product
            assert line.quantity == q
            assert basket.get_lines()
            assert basket.get_product_ids_and_quantities().get(product.pk) == q
            assert basket.product_count == q
            basket.save()
            delattr(request, "basket")
            basket = get_basket(request)
            assert basket.get_product_ids_and_quantities().get(product.pk) == q
            if is_database:
                product_ids = set(StoredBasket.objects.last().products.values_list("id", flat=True))
                assert product_ids == set([product.pk])

        if is_database:
            stats = StoredBasket.objects.all().aggregate(
                n=Sum("product_count"),
                tfs=Sum("taxful_total_price_value"),
                tls=Sum("taxless_total_price_value"),
            )
            assert stats["n"] == sum(quantities)
            if shop.prices_include_tax:
                assert stats["tfs"] == sum(quantities) * 50
            else:
                assert stats["tls"] == sum(quantities) * 50

        basket.finalize()
예제 #9
0
def get_frontend_order_state(contact, valid_lines=True):
    """
    Get a dict structure mirroring what the frontend JavaScript would submit.
    :type contact: Contact|None
    """
    translation.activate("en")
    shop = get_default_shop()
    tax = Tax.objects.create(code="test_code", rate=decimal.Decimal("0.20"), name="Default")
    tax_class = TaxClass.objects.create(identifier="test_tax_class", name="Default")
    rule = TaxRule.objects.create(tax=tax)
    rule.tax_classes.add(tax_class)
    rule.save()
    product = create_product(
        sku=printable_gibberish(),
        supplier=get_default_supplier(),
        shop=shop
    )
    product.tax_class = tax_class
    product.save()
    if valid_lines:
        lines = [
            {"id": "x", "type": "product", "product": {"id": product.id}, "quantity": "32", "baseUnitPrice": 50},
            {"id": "y", "type": "other", "sku": "hello", "text": "A greeting", "quantity": 1, "unitPrice": "5.5"},
            {"id": "z", "type": "text", "text": "This was an order!", "quantity": 0},
        ]
    else:
        unshopped_product = create_product(sku=printable_gibberish(), supplier=get_default_supplier())
        not_visible_product = create_product(
            sku=printable_gibberish(),
            supplier=get_default_supplier(),
            shop=shop
        )
        not_visible_shop_product = not_visible_product.get_shop_instance(shop)
        not_visible_shop_product.visible = False
        not_visible_shop_product.save()
        lines = [
            {"id": "x", "type": "product"},  # no product?
            {"id": "x", "type": "product", "product": {"id": unshopped_product.id}},  # not in this shop?
            {"id": "y", "type": "product", "product": {"id": -product.id}},  # invalid product?
            {"id": "z", "type": "other", "quantity": 1, "unitPrice": "q"},  # what's that price?
            {"id": "rr", "type": "product", "quantity": 1, "product": {"id": not_visible_product.id}}  # not visible
        ]

    state = {
        "customer": {"id": contact.id if contact else None},
        "lines": lines,
        "methods": {
            "shippingMethod": {"id": get_default_shipping_method().id},
            "paymentMethod": {"id": get_default_payment_method().id},
        },
        "shop": {
            "selected": {
                "id": shop.id,
                "name": shop.name,
                "currency": shop.currency,
                "priceIncludeTaxes": shop.prices_include_tax
            }
        }
    }
    return state
예제 #10
0
def get_order_and_source(admin_user, product):
    # create original source to tamper with
    source = BasketishOrderSource(get_default_shop())
    source.status = get_initial_order_status()
    source.billing_address = MutableAddress.objects.create(name="Original Billing")
    source.shipping_address = MutableAddress.objects.create(name="Original Shipping")
    source.customer = get_person_contact(admin_user)
    source.payment_method = get_default_payment_method()
    source.shipping_method = get_default_shipping_method()
    source.add_line(
        type=OrderLineType.PRODUCT,
        product=product,
        supplier=get_default_supplier(),
        quantity=1,
        base_unit_price=source.create_price(10),
    )
    source.add_line(
        type=OrderLineType.OTHER,
        quantity=1,
        base_unit_price=source.create_price(10),
        require_verification=True,
    )
    assert len(source.get_lines()) == 2
    source.creator = admin_user
    creator = OrderCreator()
    order = creator.create_order(source)
    return order, source
예제 #11
0
def seed_source(user, shop):
    source = BasketishOrderSource(shop)
    source.status = get_initial_order_status()
    source.customer = get_person_contact(user)
    source.payment_method = get_default_payment_method()
    source.shipping_method = get_default_shipping_method()
    return source
def test_single_page_checkout_with_login_and_register(browser, live_server, settings):
    # initialize
    product_name = "Test Product"
    get_default_shop()
    pm = get_default_payment_method()
    sm = get_default_shipping_method()
    product = create_orderable_product(product_name, "test-123", price=100)
    OrderStatus.objects.create(
        identifier="initial",
        role=OrderStatusRole.INITIAL,
        name="initial",
        default=True
    )

    # Initialize test and go to front page
    browser = initialize_front_browser_test(browser, live_server)

    wait_until_condition(browser, lambda x: x.is_text_present("Welcome to Default!"))
    navigate_to_checkout(browser, product)

    # Let's assume that after addresses the checkout is normal
    wait_until_condition(browser, lambda x: x.is_text_present("Checkout Method"))
    test_username = "******"
    test_email = "*****@*****.**"
    test_password = "******"
    register_test(browser, live_server, test_username, test_email, test_password)

    login_and_finish_up_the_checkout(browser, live_server, test_username, test_email, test_password)
예제 #13
0
def create_simple_order(request, creator, customer):
    billing_address = get_address().to_immutable()
    shipping_address = get_address(name="Shippy Doge").to_immutable()
    shipping_address.save()
    shop = request.shop
    order = Order(
        creator=creator,
        customer=customer,
        shop=shop,
        payment_method=get_default_payment_method(),
        shipping_method=get_default_shipping_method(),
        billing_address=billing_address,
        shipping_address=shipping_address,
        order_date=now(),
        status=get_initial_order_status(),
        currency=shop.currency,
        prices_include_tax=shop.prices_include_tax,
    )
    order.full_clean()
    order.save()

    order.cache_prices()
    order.check_all_verified()
    order.save()
    return order
예제 #14
0
def test_model_form_partially_translated(rf, admin_user):
    with override_settings(**{"LANGUAGES": (("en", "en"), ("fi", "fi"), ("ja", "ja")),
                              "PARLER_DEFAULT_LANGUAGE_CODE": "en"}):
        activate("en")
        get_default_shop()
        request = apply_request_middleware(rf.get("/"), user=admin_user)
        test_name_en = "Test shop"
        payment_method = get_default_payment_method()
        payment_method.name = test_name_en
        payment_method.save()

        form = PaymentMethodForm(instance=payment_method, request=request, languages=settings.LANGUAGES)
        data = get_form_data(form, prepared=True)
        assert data.get("name__en") == test_name_en
        assert not data.get("name__fi")
        form = PaymentMethodForm(data=data, instance=payment_method, request=request, languages=settings.LANGUAGES)
        form.full_clean()
        assert form.is_valid() and not form.errors
        payment_method = form.save()

        # Add description for Finnish and and name in Finnish should be required
        data["description__fi"] = "Some description"
        form = PaymentMethodForm(data=data, instance=payment_method, request=request, languages=settings.LANGUAGES)
        form.full_clean()
        assert not form.is_valid() and form.errors

        test_name_fi = "Some method name in finnish"
        data["name__fi"] = test_name_fi
        form = PaymentMethodForm(data=data, instance=payment_method, request=request, languages=settings.LANGUAGES)
        form.full_clean()
        assert form.is_valid() and not form.errors
        payment_method = form.save()

        assert payment_method.name == test_name_en, "Object in English"

        activate("fi")
        payment_method.set_current_language("fi")
        assert payment_method.name == test_name_fi, "Object in Finnish"

        activate("ja")
        payment_method.set_current_language("ja")
        assert payment_method.name == test_name_en, "Should fallback to English"

        # Check that no sneaky translations is not created for Japan
        with pytest.raises(ObjectDoesNotExist):
            translation = payment_method.get_translation("ja")
            translation.refresh_from_db()  # Just in case if the translation object comes from cache or something

        # Empty finnish translations and see if Finnish starts fallbacks too
        data["name__fi"] = data["description__fi"] = ""
        form = PaymentMethodForm(data=data, instance=payment_method, request=request, languages=settings.LANGUAGES)
        form.full_clean()
        assert form.is_valid() and not form.errors
        form.save()

        # Check that no sneaky translations is not created for Finnish
        with pytest.raises(ObjectDoesNotExist):
            translation = payment_method.get_translation("fi")
            translation.refresh_from_db()  # Just in case if the translation object comes from cache or something
예제 #15
0
def test_unsaved_contact(admin_user):
    payment_method = get_default_payment_method()
    _assign_component_for_service(payment_method, [PersonContact.get_default_group()])
    person = PersonContact(name="Kalle")
    source = _get_source_for_contact(admin_user, payment_method)
    source.customer = person
    assert not person.pk and not source.customer.pk
    _test_service_availability(source, payment_method, False)
예제 #16
0
def _save_cart_with_products(rf, user):
    shop = get_default_shop()
    person = get_person_contact(user)
    get_default_payment_method()
    get_default_shipping_method()
    request = rf.post("/", {"title": "test"})
    request.shop = shop
    request.user = user
    request.person = person
    request.customer = person
    basket = get_basket(request)
    request = apply_request_middleware(request, user=user, person=person, customer=person, basket=basket)
    basket = _add_products_to_basket(basket)
    basket.save()
    response = CartSaveView.as_view()(request)
    basket = StoredBasket.objects.filter(title="test").first()
    data = json.loads(response.content.decode("utf8"))
    assert data["ok"], "cart saved successfully"
    return basket
예제 #17
0
def test_without_groups(admin_user):
    payment_method = get_default_payment_method()
    _assign_component_for_service(payment_method, [])

    person = create_random_person()
    person.user = admin_user
    person.save()
    source = _get_source_for_contact(admin_user, payment_method)
    assert source.customer == person
    _test_service_availability(source, payment_method, False)
예제 #18
0
def test_coupon(browser, live_server, settings):
    activate("en")
    # initialize
    cache.clear()
    shop = get_default_shop()
    get_default_payment_method()
    get_default_shipping_method()

    first_category = Category.objects.create(
        identifier="cat-1", status=CategoryStatus.VISIBLE, name="First Category")
    first_category.shops.add(shop)

    _populate_products_form_data(CATEGORY_PRODUCT_DATA, shop, first_category)

    # initialize test and go to front page
    browser = initialize_front_browser_test(browser, live_server)

    _add_product_to_basket_from_category(live_server, browser, first_category, shop)
    _activate_basket_campaign_through_coupon(browser, first_category, shop)
예제 #19
0
def seed_source(user, extra_addr=True):
    source = BasketishOrderSource(get_default_shop())
    billing_address = get_address()
    shipping_address = get_address(name="Shippy Doge")

    if extra_addr:
        billing_address.extra = ExtraMutableAddress.from_data(EXTRA_MUTABLE_ADDRESS_1)
    if extra_addr:
        shipping_address.extra = ExtraMutableAddress.from_data(EXTRA_MUTABLE_ADDRESS_2)

    source.status = get_initial_order_status()
    source.billing_address = billing_address
    source.shipping_address = shipping_address
    source.customer = get_person_contact(user)
    source.payment_method = get_default_payment_method()
    source.shipping_method = get_default_shipping_method()
    assert source.payment_method_id == get_default_payment_method().id
    assert source.shipping_method_id == get_default_shipping_method().id
    return source
예제 #20
0
def test_add_product_to_basket_with_custom_shop_product_fields(admin_user, settings):
    product_name = "Product Name"
    shop_product_name = "SHOP Product Name"

    configure(settings)
    shop = factories.get_default_shop()
    basket = factories.get_basket()
    factories.get_default_payment_method()
    factories.get_default_shipping_method()
    shop_product = factories.get_default_shop_product()
    shop_product.default_price = TaxfulPrice(1, shop.currency)
    shop_product.save()

    shop_product.product.name = product_name
    shop_product.product.save()
    client = _get_client(admin_user)

    payload = {
        'product': shop_product.product.pk,
        'shop': shop.pk
    }
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_200_OK

    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1
    assert response_data["items"][0]["shop_product"] == shop_product.pk
    assert response_data["items"][0]["text"] == product_name

    # set shop product name
    shop_product.product.name = shop_product_name
    shop_product.product.save()

    # add product
    payload = {
        'product': shop_product.product.pk,
        'shop': shop.pk
    }
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == status.HTTP_200_OK
    response_data = json.loads(response.content.decode("utf-8"))
    assert len(response_data["items"]) == 1
    assert response_data["items"][0]["text"] == shop_product_name
예제 #21
0
def test_fetch_basket(admin_user, settings):
    configure(settings)
    shop = factories.get_default_shop()
    shop2 = create_shop("foobar")
    basket = factories.get_basket()
    factories.get_default_payment_method()
    factories.get_default_shipping_method()
    assert basket.shop == shop
    client = _get_client(admin_user)
    response = client.get('/api/shuup/basket/{}-{}/'.format(shop.pk, basket.key))
    assert response.status_code == status.HTTP_200_OK
    basket_data = json.loads(response.content.decode("utf-8"))
    assert basket_data["key"] == basket.key
    assert not basket_data["validation_errors"]
    # malformed uuid
    response = client.get('/api/shuup/basket/{}/'.format(basket.key))
    assert response.status_code == status.HTTP_400_BAD_REQUEST
    # wrong shop
    response = client.get('/api/shuup/basket/{}-{}/'.format(shop2.pk, basket.key))
    assert response.status_code == 400
예제 #22
0
def test_with_multiple_groups(admin_user):
    payment_method = get_default_payment_method()
    group = get_default_customer_group()
    person = create_random_person()
    groups = [group, person.get_default_group()]
    _assign_component_for_service(payment_method, groups)

    person.user = admin_user
    person.save()
    source = _get_source_for_contact(admin_user, payment_method)
    assert source.customer == person
    assert len([group for group in person.groups.all() if group in groups]) == 1
    _test_service_availability(source, payment_method, True)
예제 #23
0
def test_add_product_shop_mismatch(admin_user, settings):
    configure(settings)
    shop = factories.get_default_shop()
    shop2 = create_shop("foobar")
    basket = factories.get_basket()
    factories.get_default_payment_method()
    factories.get_default_shipping_method()
    sp = factories.create_product("test", shop=shop2, supplier=factories.get_default_supplier()).get_shop_instance(shop2)
    client = _get_client(admin_user)
    payload = {
        'shop_product': sp.id
    }
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == 400
    assert "different shop" in str(response.content)

    # add product belonging to different shop than basket shop
    payload = {
        'shop': sp.shop.id,
        'product': sp.product.id
    }
    response = client.post('/api/shuup/basket/{}-{}/add/'.format(shop.pk, basket.key), payload)
    assert response.status_code == 400
    assert "different shop" in str(response.content)
예제 #24
0
def test_order_create_without_default_address(admin_user):
    create_default_order_statuses()
    shop = get_default_shop()
    sm = get_default_shipping_method()
    pm = get_default_payment_method()
    contact = create_random_person(locale="en_US", minimum_name_comp_len=5)
    contact.default_billing_address = None
    contact.default_shipping_address = None
    contact.save()
    product = create_product(
        sku=printable_gibberish(),
        supplier=get_default_supplier(),
        shop=shop
    )
    assert not Order.objects.count()
    client = _get_client(admin_user)
    lines = [
        {"type": "product", "product": product.id, "quantity": "1", "base_unit_price_value": "5.00"},
        {"type": "product", "product": product.id, "quantity": "2", "base_unit_price_value": "1.00", "discount_amount_value": "0.50"},
        {"type": "other", "sku": "hello", "text": "A greeting", "quantity": 1, "base_unit_price_value": "3.5"},
        {"type": "text", "text": "This was an order!", "quantity": 0},
    ]
    response = client.post("/api/shuup/order/", content_type="application/json", data=json.dumps({
        "shop": shop.pk,
        "shipping_method": sm.pk,
        "payment_method": pm.pk,
        "customer": contact.pk,
        "lines": lines
    }))
    assert response.status_code == 201
    assert Order.objects.count() == 1
    order = Order.objects.first()
    assert order.shop == shop
    assert order.shipping_method == sm
    assert order.payment_method == pm
    assert order.customer == contact
    assert order.creator == admin_user
    assert order.billing_address is None
    assert order.shipping_address is None
    assert order.payment_status == PaymentStatus.NOT_PAID
    assert order.shipping_status == ShippingStatus.NOT_SHIPPED
    assert order.status == OrderStatus.objects.get_default_initial()
    assert order.taxful_total_price_value == decimal.Decimal(10)
    assert order.lines.count() == 6 # shipping line, payment line, 2 product lines, 2 other lines
    for idx, line in enumerate(order.lines.all()[:4]):
        assert line.quantity == decimal.Decimal(lines[idx].get("quantity"))
        assert line.base_unit_price_value == decimal.Decimal(lines[idx].get("base_unit_price_value", 0))
        assert line.discount_amount_value == decimal.Decimal(lines[idx].get("discount_amount_value", 0))
예제 #25
0
def test_contact_group_behavior(admin_user):
    payment_method = get_default_payment_method()
    group = get_default_customer_group()
    _assign_component_for_service(payment_method, [group])

    person = create_random_person()
    person.user = admin_user
    person.save()
    source = _get_source_for_contact(admin_user, payment_method)
    assert source.customer == person
    assert group not in person.groups.all()
    _test_service_availability(source, payment_method, False)

    person.groups.add(group)
    assert group in person.groups.all()
    _test_service_availability(source, payment_method, True)
예제 #26
0
def test_order_creator_view(browser, admin_user, live_server):
    shop = get_default_shop()
    pm = get_default_payment_method()
    sm = get_default_shipping_method()
    get_initial_order_status()
    supplier = get_default_supplier()
    person = create_random_person()
    product0 = create_product("test-sku0", shop=shop, default_price=10, supplier=supplier)
    product1 = create_product("test-sku1", shop=shop, default_price=10, supplier=supplier)

    initialize_admin_browser_test(browser, live_server)
    _visit_order_creator_view(browser, live_server)
    _test_customer_data(browser, person)
    _test_add_lines(browser)
    _test_quick_add_lines(browser)
    _test_methods(browser)
    _test_confirm(browser)
예제 #27
0
def seed_source(shipping_method=None, produce_price=10):
    source = BasketishOrderSource(get_default_shop())
    billing_address = get_address()
    shipping_address = get_address(name="Shippy Doge")
    source.status = get_initial_order_status()
    source.billing_address = billing_address
    source.shipping_address = shipping_address
    source.customer = create_random_person()
    source.payment_method = get_default_payment_method()
    source.shipping_method = shipping_method if shipping_method else get_default_shipping_method()
    source.add_line(
        type=OrderLineType.PRODUCT,
        product=get_default_product(),
        supplier=get_default_supplier(),
        quantity=1,
        base_unit_price=source.create_price(produce_price),
    )
    return source
예제 #28
0
def test_staff_only_behavior(admin_user, regular_user):
    payment_method = get_default_payment_method()
    component = StaffOnlyBehaviorComponent.objects.create()
    payment_method.behavior_components.add(component)
    source = BasketishOrderSource(get_default_shop())

    # anonymous user
    unavailability_reasons = list(payment_method.get_unavailability_reasons(source))
    assert len(unavailability_reasons) == 1

    # regular user
    source.creator = regular_user
    unavailability_reasons = list(payment_method.get_unavailability_reasons(source))
    assert len(unavailability_reasons) == 1

    # admin
    source.creator = admin_user
    unavailability_reasons = list(payment_method.get_unavailability_reasons(source))
    assert len(unavailability_reasons) == 0
예제 #29
0
def get_order_and_source(admin_user, product, language, language_fallback):
    # create original source to tamper with

    contact = get_person_contact(admin_user)
    contact.language = language
    contact.save()

    assert contact.language == language  # contact language is naive

    source = BasketishOrderSource(get_default_shop())
    source.status = get_initial_order_status()
    source.billing_address = MutableAddress.objects.create(name="Original Billing")
    source.shipping_address = MutableAddress.objects.create(name="Original Shipping")
    source.customer = contact
    source.payment_method = get_default_payment_method()
    source.shipping_method = get_default_shipping_method()
    source.add_line(
        type=OrderLineType.PRODUCT,
        product=product,
        supplier=get_default_supplier(),
        quantity=1,
        base_unit_price=source.create_price(10),
    )
    source.add_line(
        type=OrderLineType.OTHER,
        quantity=1,
        base_unit_price=source.create_price(10),
        require_verification=True,
    )
    assert len(source.get_lines()) == 2
    source.creator = admin_user

    assert not source._language  # is None because it was not directly assigned
    assert source.language == language_fallback

    creator = OrderCreator()
    order = creator.create_order(source)

    assert order.language == source.language

    return order, source
예제 #30
0
def test_order_creator_view(browser, admin_user, live_server, settings):
    shop = get_default_shop()
    pm = get_default_payment_method()
    sm = get_default_shipping_method()
    get_initial_order_status()
    supplier = get_default_supplier()
    person = create_random_person()
    product0 = create_product("test-sku0", shop=shop, default_price=10, supplier=supplier)
    product1 = create_product("test-sku1", shop=shop, default_price=10, supplier=supplier)
    object_created.connect(_add_custom_order_created_message, sender=Order, dispatch_uid="object_created_signal_test")
    initialize_admin_browser_test(browser, live_server, settings)
    browser.driver.maximize_window()
    _visit_order_creator_view(browser, live_server)
    _test_language_change(browser)
    _test_customer_data(browser, person)
    _test_regions(browser, person)
    _test_add_lines(browser)
    _test_quick_add_lines(browser)
    _test_methods(browser)
    _test_confirm(browser)
    assert Order.objects.first().log_entries.filter(identifier=OBJECT_CREATED_LOG_IDENTIFIER).count() == 1
    object_created.disconnect(sender=Order, dispatch_uid="object_created_signal_test")
예제 #31
0
def test_browser_checkout_vertical(browser, live_server, reindex_catalog):
    with override_settings(SHUUP_CHECKOUT_VIEW_SPEC=(
            "shuup.front.views.checkout:SinglePageCheckoutView")):
        # initialize
        product_name = "Test Product"
        get_default_shop()
        pm = get_default_payment_method()
        sm = get_default_shipping_method()
        product = create_orderable_product(product_name, "test-123", price=100)
        reindex_catalog()
        OrderStatus.objects.create(identifier="initial",
                                   role=OrderStatusRole.INITIAL,
                                   name="initial",
                                   default=True)

        # initialize test and go to front page
        browser = initialize_front_browser_test(browser, live_server)
        # check that front page actually loaded
        wait_until_condition(
            browser, lambda x: x.is_text_present("Welcome to Default!"))
        wait_until_condition(browser,
                             lambda x: x.is_text_present("Newest Products"))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(product_name))

        click_element(browser, "#product-%s" %
                      product.pk)  # open product from product list
        click_element(browser, "#add-to-cart-button-%s" %
                      product.pk)  # add product to basket

        wait_until_appeared(browser, ".cover-wrap")
        wait_until_disappeared(browser, ".cover-wrap")

        click_element(
            browser,
            "#navigation-basket-partial")  # open upper basket navigation menu
        click_element(
            browser,
            "a[href='/basket/']")  # click the link to basket in dropdown
        wait_until_condition(browser, lambda x: x.is_text_present(
            "Shopping cart"))  # we are in basket page
        wait_until_condition(
            browser,
            lambda x: x.is_text_present(product_name))  # product is in basket

        click_element(
            browser,
            "a[href='/checkout/']")  # click link that leads to checkout
        wait_until_appeared(browser, "h4.panel-title")
        customer_name = "Test Tester"
        customer_street = "Test Street"
        customer_city = "Test City"
        customer_region = "CA"
        customer_country = "US"

        # Fill all necessary information
        browser.fill("billing-name", customer_name)
        browser.fill("billing-street", customer_street)
        browser.fill("billing-city", customer_city)
        browser.select("billing-country", customer_country)
        wait_until_appeared(browser, "select[name='billing-region_code']")
        browser.select("billing-region_code", customer_region)

        click_element(browser, "#addresses button[type='submit']")

        click_element(browser, "#addresses button[type='submit']"
                      )  # This shouldn't submit since missing required fields

        # Fill rest of the fields
        browser.fill("shipping-name", customer_name)
        browser.fill("shipping-street", customer_street)
        browser.fill("shipping-city", customer_city)
        browser.select("shipping-country", customer_country)

        click_element(browser, "#addresses button[type='submit']")
        wait_until_condition(browser,
                             lambda x: x.is_text_present("Shipping & Payment"))

        wait_until_condition(browser, lambda x: x.is_text_present(sm.name)
                             )  # shipping method name is present
        wait_until_condition(browser, lambda x: x.is_text_present(pm.name)
                             )  # payment method name is present

        click_element(browser, ".btn.btn-primary.btn-lg.pull-right"
                      )  # click "continue" on methods page

        wait_until_condition(browser, lambda x: x.is_text_present(
            "Confirmation"))  # we are indeed in confirmation page

        # See that all expected texts are present
        wait_until_condition(browser,
                             lambda x: x.is_text_present(product_name))
        wait_until_condition(browser, lambda x: x.is_text_present(sm.name))
        wait_until_condition(browser, lambda x: x.is_text_present(pm.name))
        wait_until_condition(browser, lambda x: x.is_text_present("Delivery"))
        wait_until_condition(browser, lambda x: x.is_text_present("Billing"))

        # check that user information is available
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_name))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_street))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_city))
        wait_until_condition(browser,
                             lambda x: x.is_text_present("United States"))

        browser.execute_script(
            'document.getElementById("id_accept_terms").checked=true'
        )  # click accept terms
        click_element(browser,
                      ".btn.btn-primary.btn-lg")  # click "place order"

        wait_until_condition(browser, lambda x: x.is_text_present(
            "Thank you for your order!"))  # order succeeded
예제 #32
0
def login_and_finish_up_the_checkout(browser, live_server, test_username, test_email, test_password):
    fields = browser.driver.find_elements_by_name("login-username")
    # there should be only a single username field
    assert len(fields) == 1

    browser.fill("login-username", test_email)
    browser.fill("login-password", test_password)
    click_element(browser, "button[name='login']")

    wait_until_condition(browser, lambda x: x.is_text_present("Addresses"), timeout=100)
    # Reload here just in case since there might have been reload with JS
    # which might cause issues with tests since the elements is in cache
    browser.reload()

    # This should be first order upcoming
    assert Order.objects.count() == 0

    # Fnish the checkout
    customer_name = "Test Tester"
    customer_street = "Test Street"
    customer_city = "Test City"
    customer_region = "CA"
    customer_country = "US"

    # Fill all necessary information
    browser.fill("billing-name", customer_name)
    browser.fill("billing-street", customer_street)
    browser.fill("billing-city", customer_city)
    wait_until_appeared(browser, "#id_billing-region")
    browser.select("billing-country", customer_country)
    wait_until_disappeared(browser, "#id_billing-region")
    wait_until_appeared(browser, "select[name='billing-region_code']")
    browser.select("billing-region_code", customer_region)

    click_element(browser, "#addresses button[type='submit']")  # Shouldn't submit since required fields

    browser.fill("shipping-name", customer_name)
    browser.fill("shipping-street", customer_street)
    browser.fill("shipping-city", customer_city)
    wait_until_appeared(browser, "#id_shipping-region")
    browser.select("shipping-country", customer_country)
    wait_until_disappeared(browser, "#id_shipping-region")
    wait_until_appeared(browser, "select[name='shipping-region_code']")

    click_element(browser, "#addresses button[type='submit']")
    wait_until_condition(browser, lambda x: x.is_text_present("Shipping & Payment"))

    pm = get_default_payment_method()
    sm = get_default_shipping_method()

    wait_until_condition(browser, lambda x: x.is_text_present(sm.name))  # shipping method name is present
    wait_until_condition(browser, lambda x: x.is_text_present(pm.name))  # payment method name is present

    click_element(browser, ".btn.btn-primary.btn-lg.pull-right")  # click "continue" on methods page

    wait_until_condition(browser, lambda x: x.is_text_present("Confirmation"))  # we are indeed in confirmation page
    product = Product.objects.first()

    # See that all expected texts are present
    wait_until_condition(browser, lambda x: x.is_text_present(product.name))
    wait_until_condition(browser, lambda x: x.is_text_present(sm.name))
    wait_until_condition(browser, lambda x: x.is_text_present(pm.name))
    wait_until_condition(browser, lambda x: x.is_text_present("Delivery"))
    wait_until_condition(browser, lambda x: x.is_text_present("Billing"))

    # check that user information is available
    wait_until_condition(browser, lambda x: x.is_text_present(customer_name))
    wait_until_condition(browser, lambda x: x.is_text_present(customer_street))
    wait_until_condition(browser, lambda x: x.is_text_present(customer_city))
    wait_until_condition(browser, lambda x: x.is_text_present("United States"))

    browser.execute_script('document.getElementById("id_accept_terms").checked=true')  # click accept terms
    click_element(browser, ".btn.btn-primary.btn-lg")  # click "place order"

    wait_until_condition(browser, lambda x: x.is_text_present("Thank you for your order!"))  # order succeeded

    # Let's make sure the order now has a customer
    assert Order.objects.count() == 1
    order = Order.objects.first()
    assert order.customer == PersonContact.objects.filter(user__username=test_username).first()
    assert order.customer.name == customer_name
    assert order.customer.default_shipping_address is not None
    assert order.customer.default_billing_address is not None
    assert order.customer.user.username == test_username
예제 #33
0
def test_browser_checkout_disable_methods(browser, live_server,
                                          reindex_catalog, delete_method):
    product_name = "Test Product"
    get_default_shop()

    payment_method = get_default_payment_method()
    shipping_method = get_default_shipping_method()

    product = create_orderable_product(product_name, "test-123", price=100)
    reindex_catalog()
    OrderStatus.objects.create(identifier="initial",
                               role=OrderStatusRole.INITIAL,
                               name="initial",
                               default=True)

    # initialize test and go to front page
    browser = initialize_front_browser_test(browser, live_server)

    # check that front page actually loaded
    wait_until_condition(browser,
                         lambda x: x.is_text_present("Welcome to Default!"))
    wait_until_condition(browser,
                         lambda x: x.is_text_present("Newest Products"))
    wait_until_condition(browser, lambda x: x.is_text_present(product_name))

    click_element(browser,
                  "#product-%s" % product.pk)  # open product from product list
    click_element(browser, "#add-to-cart-button-%s" %
                  product.pk)  # add product to basket

    wait_until_appeared(browser, ".cover-wrap")
    wait_until_disappeared(browser, ".cover-wrap")

    click_element(
        browser,
        "#navigation-basket-partial")  # open upper basket navigation menu
    click_element(browser,
                  "a[href='/basket/']")  # click the link to basket in dropdown
    wait_until_condition(
        browser,
        lambda x: x.is_text_present("Shopping cart"))  # we are in basket page
    wait_until_condition(
        browser,
        lambda x: x.is_text_present(product_name))  # product is in basket

    click_element(browser,
                  "a[href='/checkout/']")  # click link that leads to checkout

    customer_name = "Test Tester"
    customer_street = "Test Street"
    customer_city = "Test City"
    customer_region = "CA"
    customer_country = "US"

    # Fill all necessary information
    browser.fill("billing-name", customer_name)
    browser.fill("billing-street", customer_street)
    browser.fill("billing-city", customer_city)
    browser.select("billing-country", customer_country)
    wait_until_appeared(browser, "select[name='billing-region_code']")
    browser.select("billing-region_code", customer_region)

    browser.fill("billing-name", customer_name)
    browser.fill("billing-street", customer_street)
    browser.fill("billing-city", customer_city)
    browser.select("billing-country", customer_country)
    wait_until_appeared(browser, "select[name='billing-region_code']")
    browser.select("billing-region_code", customer_region)

    click_element(browser, "#addresses button[type='submit']"
                  )  # This shouldn't submit since missing required fields

    # Fill rest of the fields
    browser.fill("shipping-name", customer_name)
    browser.fill("shipping-street", customer_street)
    browser.fill("shipping-city", customer_city)
    browser.select("shipping-country", customer_country)

    click_element(browser, "#addresses button[type='submit']")
    wait_until_condition(
        browser, lambda x: x.is_text_present("Checkout: Shipping & Payment"))
    wait_until_condition(browser,
                         lambda x: x.is_text_present(payment_method.name))
    wait_until_condition(browser,
                         lambda x: x.is_text_present(shipping_method.name))

    browser.find_by_css("input[name='shipping_method'][value='%d']" %
                        shipping_method.pk).first.click()
    browser.find_by_css("input[name='payment_method'][value='%d']" %
                        payment_method.pk).first.click()

    click_element(browser, ".btn.btn-primary.btn-lg.pull-right"
                  )  # click "continue" on methods page
    wait_until_condition(browser, lambda x: x.is_text_present(
        "Checkout: Confirmation"))  # we are indeed in confirmation page

    if delete_method == "payment":
        payment_method.delete()
    else:
        shipping_method.delete()

    click_element(browser, "a[href='/checkout/methods/']")

    wait_until_condition(
        browser, lambda x: x.is_text_present("Checkout: Shipping & Payment"))

    if delete_method == "payment":
        wait_until_condition(
            browser, lambda x: x.is_text_present("No method is available."))
        wait_until_condition(
            browser, lambda x: not x.is_text_present(payment_method.name))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(shipping_method.name))
    else:
        wait_until_condition(
            browser, lambda x: x.is_text_present("No method is available."))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(payment_method.name))
        wait_until_condition(
            browser, lambda x: not x.is_text_present(shipping_method.name))
예제 #34
0
def get_frontend_order_state(contact, valid_lines=True):
    """
    Get a dict structure mirroring what the frontend JavaScript would submit.
    :type contact: Contact|None
    """
    translation.activate("en")
    shop = get_default_shop()
    tax, created = Tax.objects.get_or_create(code="test_code", defaults={"rate": decimal.Decimal("0.20"),
                                                                         "name": "Default"})
    tax_class, created = TaxClass.objects.get_or_create(identifier="test_tax_class", defaults={"name": "Default"})
    rule, created = TaxRule.objects.get_or_create(tax=tax)
    rule.tax_classes.add(tax_class)
    rule.save()
    product = create_product(
        sku=printable_gibberish(),
        supplier=get_default_supplier(),
        shop=shop
    )
    product.tax_class = tax_class
    product.save()
    if valid_lines:
        lines = [
            {"id": "x", "type": "product", "product": {"id": product.id}, "quantity": "32", "baseUnitPrice": 50},
            {"id": "y", "type": "other", "sku": "hello", "text": "A greeting", "quantity": 1, "unitPrice": "5.5"},
            {"id": "z", "type": "text", "text": "This was an order!", "quantity": 0},
        ]
    else:
        unshopped_product = create_product(sku=printable_gibberish(), supplier=get_default_supplier())
        not_visible_product = create_product(
            sku=printable_gibberish(),
            supplier=get_default_supplier(),
            shop=shop
        )
        not_visible_shop_product = not_visible_product.get_shop_instance(shop)
        not_visible_shop_product.visibility = ShopProductVisibility.NOT_VISIBLE
        not_visible_shop_product.save()
        lines = [
            {"id": "x", "type": "product"},  # no product?
            {"id": "x", "type": "product", "product": {"id": unshopped_product.id}},  # not in this shop?
            {"id": "y", "type": "product", "product": {"id": -product.id}},  # invalid product?
            {"id": "z", "type": "other", "quantity": 1, "unitPrice": "q"},  # what's that price?
            {"id": "rr", "type": "product", "quantity": 1, "product": {"id": not_visible_product.id}}  # not visible
        ]
    state = {
        "customer": {
            "id": contact.id if contact else None,
            "billingAddress": encode_address(contact.default_billing_address) if contact else {},
            "shippingAddress": encode_address(contact.default_shipping_address) if contact else {},
        },
        "lines": lines,
        "methods": {
            "shippingMethod": {"id": get_default_shipping_method().id},
            "paymentMethod": {"id": get_default_payment_method().id},
        },
        "shop": {
            "selected": {
                "id": shop.id,
                "name": shop.name,
                "currency": shop.currency,
                "priceIncludeTaxes": shop.prices_include_tax
            }
        }
    }
    return state
예제 #35
0
def test_create_order(admin_user, target_customer):
    with override_settings(**REQUIRED_SETTINGS):
        set_configuration()
        factories.create_default_order_statuses()
        shop = factories.get_default_shop()
        client = _get_client(admin_user)

        # Create basket for target customer
        payload = {"shop": shop.pk}
        target = orderer = get_person_contact(admin_user)
        if target_customer == "other_person":
            target = orderer = factories.create_random_person()
            payload["customer"] = target.pk
        elif target_customer == "company":
            target = factories.create_random_company()
            orderer = factories.create_random_person()
            payload.update({"customer": target.pk, "orderer": orderer.pk})
            target.members.add(orderer)

        response = client.post("/api/shuup/basket/new/", payload)
        assert response.status_code == status.HTTP_201_CREATED
        basket_data = json.loads(response.content.decode("utf-8"))
        basket = Basket.objects.first()
        assert basket.key == basket_data["uuid"].split("-")[1]
        assert basket.customer == target
        assert basket.orderer == orderer

        shop_product = factories.get_default_shop_product()
        shop_product.default_price = TaxfulPrice(1, shop.currency)
        shop_product.save()

        # Add shop product to basket
        payload = {"shop_product": shop_product.id}
        response = client.post(
            "/api/shuup/basket/{}-{}/add/".format(shop.pk, basket.key),
            payload)
        assert response.status_code == status.HTTP_200_OK
        response_data = json.loads(response.content.decode("utf-8"))
        assert len(response_data["items"]) == 1

        # Create order from basket
        response = client.post(
            "/api/shuup/basket/{}-{}/create_order/".format(
                shop.pk, basket.key), payload)
        assert response.status_code == status.HTTP_400_BAD_REQUEST
        response_data = json.loads(response.content.decode("utf-8"))
        assert "errors" in response_data

        factories.get_default_payment_method()
        factories.get_default_shipping_method()
        response = client.post(
            "/api/shuup/basket/{}-{}/create_order/".format(
                shop.pk, basket.key), payload)
        assert response.status_code == status.HTTP_201_CREATED
        response_data = json.loads(response.content.decode("utf-8"))
        basket.refresh_from_db()
        assert basket.finished
        order = Order.objects.get(
            reference_number=response_data["reference_number"])
        assert order.status == OrderStatus.objects.get_default_initial()
        assert order.payment_status == PaymentStatus.NOT_PAID
        assert order.shipping_status == ShippingStatus.NOT_SHIPPED
        assert not order.payment_method
        assert not order.shipping_method
        assert float(order.taxful_total_price_value) == 1
        assert order.customer == target
        assert order.orderer == orderer
        assert order.creator == admin_user
        assert not order.billing_address
        assert not order.shipping_address
예제 #36
0
def test_reorder_view():
    shop = factories.get_default_shop()
    factories.get_default_shipping_method()
    factories.get_default_payment_method()

    supplier1 = factories.get_supplier(SimpleSupplierModule.identifier,
                                       shop=shop)
    supplier2 = factories.get_supplier(SimpleSupplierModule.identifier,
                                       shop=shop)
    assert supplier1.pk != supplier2.pk

    product_supplier1 = factories.create_product(
        "product_supplier1",
        shop=shop,
        supplier=supplier1,
        default_price=10,
        shipping_mode=ShippingMode.NOT_SHIPPED)
    product_supplier2 = factories.create_product(
        "product_supplier2",
        shop=shop,
        supplier=supplier2,
        default_price=20,
        shipping_mode=ShippingMode.NOT_SHIPPED)

    user = factories.create_random_user("en")
    user.set_password("user")
    user.save()

    customer = factories.create_random_person("en")
    customer.user = user
    customer.save()

    order = factories.create_random_order(
        customer=customer,
        shop=shop,
        products=[product_supplier1, product_supplier2],
        completion_probability=0,
        random_products=False)
    suppliers = [line.supplier for line in order.lines.products()]
    assert supplier1 in suppliers
    assert supplier2 in suppliers

    client = Client()
    client.login(username=user.username, password="******")

    # list orders
    response = client.get(reverse("shuup:personal-orders"))
    assert response.status_code == 200
    content = response.content.decode("utf-8")
    assert "<td>%d</td>" % order.id in content
    assert "<td>Received</td>" in content

    # go to order detail
    response = client.get(reverse("shuup:show-order",
                                  kwargs=dict(pk=order.pk)))
    assert response.status_code == 200
    content = response.content.decode("utf-8")
    assert "Add all products to cart" in content
    reorder_url = reverse("shuup:reorder-order", kwargs=dict(pk=order.pk))
    assert reorder_url in content

    # reorder products
    response = client.get(reorder_url)
    assert response.status_code == 302
    assert response.url.endswith(reverse("shuup:basket"))

    # go to basket
    response = client.get(response.url)
    assert response.status_code == 200
    content = response.content.decode("utf-8")

    # ensure the basket contain those products and suppliers
    basket_key = client.session["basket_basket_key"]["key"]
    from shuup.front.models import StoredBasket
    basket = StoredBasket.objects.get(key=basket_key)
    lines = basket.data["lines"]
    product_supplier = [(line["product_id"], line["supplier_id"])
                        for line in lines]
    assert (product_supplier1.pk, supplier1.pk) in product_supplier
    assert (product_supplier2.pk, supplier2.pk) in product_supplier

    assert product_supplier1.name in content
    assert product_supplier2.name in content
    assert "You are unable to proceed to checkout!" not in content
예제 #37
0
def test_basket_reorder_staff_user():
    with override_settings(**REQUIRED_SETTINGS):
        set_configuration()
        shop = factories.get_default_shop()
        factories.get_default_payment_method()
        factories.get_default_shipping_method()
        staff_user = User.objects.create(username="******", is_staff=True)

        client = _get_client(staff_user)
        person = factories.create_random_person()

        # create an order for the person
        product = create_product("product",
                                 shop=shop,
                                 supplier=get_default_supplier(),
                                 default_price='12.4')
        order = create_random_order(customer=person,
                                    products=[product],
                                    completion_probability=1,
                                    shop=shop)

        # create the basket
        response = client.post("/api/shuup/basket/new/",
                               data={
                                   "shop": shop.pk,
                                   "customer": person.pk
                               },
                               format="json")
        # Only stuff linked to shop can create baskets for someone else
        assert response.status_code == status.HTTP_403_FORBIDDEN

        # Can still add personal baskets
        staff_person = get_person_contact(staff_user)
        response = client.post("/api/shuup/basket/new/",
                               data={
                                   "shop": shop.pk,
                                   "customer": staff_person.pk
                               },
                               format="json")
        assert response.status_code == status.HTTP_201_CREATED
        basket_data = json.loads(response.content.decode("utf-8"))
        basket = Basket.objects.filter(
            key=basket_data["uuid"].split("-")[1]).first()
        assert basket.shop == shop
        assert basket.creator == staff_user
        assert basket.customer.pk == staff_person.pk
        response = client.get("/api/shuup/basket/{}/".format(
            basket_data["uuid"]))
        assert response.status_code == 200

        # Ok let's link the staff member to the shop and
        # the basket create for random person should work
        shop.staff_members.add(staff_user)
        response = client.post("/api/shuup/basket/new/",
                               data={
                                   "shop": shop.pk,
                                   "customer": person.pk
                               },
                               format="json")
        assert response.status_code == status.HTTP_201_CREATED
        basket_data = json.loads(response.content.decode("utf-8"))
        basket = Basket.objects.filter(
            key=basket_data["uuid"].split("-")[1]).first()
        assert basket.shop == shop
        assert basket.creator == staff_user
        assert basket.customer.pk == person.pk
        response = client.get("/api/shuup/basket/{}/".format(
            basket_data["uuid"]))
        assert response.status_code == 200
        assert basket.creator == staff_user
        assert basket.customer.pk == person.pk

        # add contents to the basket from a customer order
        response = client.post(
            '/api/shuup/basket/{}-{}/add_from_order/'.format(
                shop.pk, basket.key),
            data={"order": order.pk},
            format="json")
        assert response.status_code == status.HTTP_200_OK
        basket_data = json.loads(response.content.decode("utf-8"))
        assert len(basket_data['items']) > 0
        assert Decimal(basket_data['taxful_total_price']
                       ) == order.taxful_total_price_value

        # finally create the order
        response = client.post('/api/shuup/basket/{}-{}/create_order/'.format(
            shop.pk, basket.key))
        assert response.status_code == status.HTTP_201_CREATED
        response_data = json.loads(response.content.decode("utf-8"))
        created_order = Order.objects.get(id=response_data['id'])
        assert created_order.creator == staff_user
        assert created_order.customer == person

        # create a second customer
        person2 = factories.create_random_person()
        # create a basket for customer 2 and try to fill with contents of customer 1 order - it should not be possible
        response = client.post("/api/shuup/basket/new/",
                               data={
                                   "shop": shop.pk,
                                   "customer": person2.pk
                               },
                               format="json")
        assert response.status_code == status.HTTP_201_CREATED
        basket_data = json.loads(response.content.decode("utf-8"))
        basket = Basket.objects.filter(
            key=basket_data["uuid"].split("-")[1]).first()
        assert basket.shop == shop
        assert basket.creator == staff_user
        assert basket.customer.pk == person2.pk

        # add contents to the basket from customer 1 order - error
        response = client.post(
            '/api/shuup/basket/{}-{}/add_from_order/'.format(
                shop.pk, basket.key),
            data={"order": order.pk},
            format="json")
        assert response.status_code == status.HTTP_404_NOT_FOUND
        assert 'invalid order' in response.content.decode("utf-8")
예제 #38
0
def test_encode_method_weights():
    payment_method = get_default_payment_method()
    assert encode_method(payment_method).get("minWeight") is None
    shipping_method = get_default_shipping_method()
    assert encode_method(shipping_method).get("minWeight") is None
예제 #39
0
def test_order_create_without_default_address(admin_user):
    create_default_order_statuses()
    shop = get_default_shop()
    sm = get_default_shipping_method()
    pm = get_default_payment_method()
    contact = create_random_person(locale="en_US", minimum_name_comp_len=5)
    contact.default_billing_address = None
    contact.default_shipping_address = None
    contact.save()
    product = create_product(sku=printable_gibberish(),
                             supplier=get_default_supplier(),
                             shop=shop)
    assert not Order.objects.count()
    client = _get_client(admin_user)
    lines = [
        {
            "type": "product",
            "product": product.id,
            "quantity": "1",
            "base_unit_price_value": "5.00"
        },
        {
            "type": "product",
            "product": product.id,
            "quantity": "2",
            "base_unit_price_value": "1.00",
            "discount_amount_value": "0.50"
        },
        {
            "type": "other",
            "sku": "hello",
            "text": "A greeting",
            "quantity": 1,
            "base_unit_price_value": "3.5"
        },
        {
            "type": "text",
            "text": "This was an order!",
            "quantity": 0
        },
    ]
    response = client.post("/api/shuup/order/",
                           content_type="application/json",
                           data=json.dumps({
                               "shop": shop.pk,
                               "shipping_method": sm.pk,
                               "payment_method": pm.pk,
                               "customer": contact.pk,
                               "lines": lines
                           }))
    assert response.status_code == 201
    assert Order.objects.count() == 1
    order = Order.objects.first()
    assert order.shop == shop
    assert order.shipping_method == sm
    assert order.payment_method == pm
    assert order.customer == contact
    assert order.creator == admin_user
    assert order.billing_address is None
    assert order.shipping_address is None
    assert order.payment_status == PaymentStatus.NOT_PAID
    assert order.shipping_status == ShippingStatus.NOT_SHIPPED
    assert order.status == OrderStatus.objects.get_default_initial()
    assert order.taxful_total_price_value == decimal.Decimal(10)
    assert order.lines.count(
    ) == 6  # shipping line, payment line, 2 product lines, 2 other lines
    for idx, line in enumerate(order.lines.all()[:4]):
        assert line.quantity == decimal.Decimal(lines[idx].get("quantity"))
        assert line.base_unit_price_value == decimal.Decimal(lines[idx].get(
            "base_unit_price_value", 0))
        assert line.discount_amount_value == decimal.Decimal(lines[idx].get(
            "discount_amount_value", 0))
예제 #40
0
def test_browser_checkout_addresses_horizontal(browser, live_server, settings):
    # initialize
    product_name = "Test Product"
    get_default_shop()
    pm = get_default_payment_method()
    sm = get_default_shipping_method()
    product = create_orderable_product(product_name, "test-123", price=100)
    OrderStatus.objects.create(identifier="initial",
                               role=OrderStatusRole.INITIAL,
                               name="initial",
                               default=True)

    # initialize test and go to front page
    browser = initialize_front_browser_test(browser, live_server)

    # check that front page actually loaded
    wait_until_condition(browser,
                         lambda x: x.is_text_present("Welcome to Default!"))
    wait_until_condition(browser,
                         lambda x: x.is_text_present("Newest Products"))
    wait_until_condition(browser, lambda x: x.is_text_present(product_name))

    click_element(browser,
                  "#product-%s" % product.pk)  # open product from product list
    click_element(browser, "#add-to-cart-button-%s" %
                  product.pk)  # add product to basket
    wait_until_appeared(browser, ".cover-wrap")
    wait_until_disappeared(browser, ".cover-wrap")

    click_element(
        browser,
        "#navigation-basket-partial")  # open upper basket navigation menu
    click_element(browser,
                  "a[href='/basket/']")  # click the link to basket in dropdown
    wait_until_condition(
        browser,
        lambda x: x.is_text_present("Shopping cart"))  # we are in basket page
    wait_until_condition(
        browser,
        lambda x: x.is_text_present(product_name))  # product is in basket

    click_element(browser,
                  "a[href='/checkout/']")  # click link that leads to checkout

    customer_name = "Test Tester"
    customer_street = "Test Street"

    customer_city1 = "Los Angeles"
    customer_city2 = "Blumenau"
    customer_city3 = "Vancouver"

    customer_region1 = "CA"
    customer_region2 = "SC"
    customer_region3 = "BC"

    customer_country1 = "US"
    customer_country2 = "BR"
    customer_country3 = "CA"

    # Fill all billing address fields with USA address
    browser.fill("billing-name", customer_name)
    browser.fill("billing-street", customer_street)
    browser.fill("billing-city", customer_city1)
    browser.select("billing-country", customer_country1)
    wait_until_appeared(browser, "select[name='billing-region_code']")
    browser.select("billing-region_code", customer_region1)

    # Fill all shipping address fields - Brazil address
    browser.fill("shipping-name", customer_name)
    browser.fill("shipping-street", customer_street)
    browser.fill("shipping-city", customer_city2)
    browser.select("shipping-country", customer_country2)
    wait_until_appeared(browser, "select[name='shipping-region_code']")
    browser.select("shipping-region_code", customer_region2)

    # Actually, click to send to billing address (copy billing to shipping)
    browser.find_by_css("label[for='same_as_billing']").first.click()

    # check whether fields are disable and the values are equals
    wait_until_condition(
        browser,
        lambda x: x.find_by_name("shipping-region_code").has_class("disabled"))
    wait_until_condition(
        browser,
        lambda x: x.find_by_name("shipping-country").has_class("disabled"))
    billing_country = browser.find_by_name("billing-country").first
    shipping_country = browser.find_by_name("shipping-country").first
    wait_until_appeared(browser, "select[name='billing-region_code']")
    wait_until_appeared(browser, "select[name='shipping-region_code']")
    billing_region_code = browser.find_by_name("billing-region_code").first
    shipping_region_code = browser.find_by_name("shipping-region_code").first
    assert billing_country.value == shipping_country.value
    assert billing_region_code.value == shipping_region_code.value

    # Actually, send to Canada
    browser.find_by_css("label[for='same_as_billing']").first.click()
    wait_until_condition(
        browser, lambda x: not x.find_by_name("shipping-region_code").
        has_class("disabled"))
    wait_until_condition(
        browser,
        lambda x: not x.find_by_name("shipping-country").has_class("disabled"))
    browser.fill("shipping-city", customer_city3)
    browser.select("shipping-country", customer_country3)
    wait_until_appeared(browser, "select[name='shipping-region_code']")
    browser.select("shipping-region_code", customer_region3)

    # continue
    click_element(browser, "#addresses button[type='submit']")

    wait_until_condition(
        browser, lambda x: x.is_text_present("Checkout: Shipping & Payment"))
    wait_until_condition(browser, lambda x: x.is_text_present(sm.name)
                         )  # shipping method name is present
    wait_until_condition(
        browser,
        lambda x: x.is_text_present(pm.name))  # payment method name is present

    # back to address phase, we want to send to Brazil nstead
    address_link = browser.find_by_text('1. Addresses')
    address_link.click()

    # all values must be there with correct saved values
    billing_country = browser.find_by_name("billing-country").first
    wait_until_appeared(browser, "select[name='billing-region_code']")
    billing_region_code = browser.find_by_name("billing-region_code").first
    shipping_country = browser.find_by_name("shipping-country").first
    wait_until_appeared(browser, "select[name='shipping-region_code']")
    shipping_region_code = browser.find_by_name("shipping-region_code").first
    assert billing_country.value == customer_country1
    assert billing_region_code.value == customer_region1
    assert shipping_country.value == customer_country3
    assert shipping_region_code.value == customer_region3

    # Fill shipping with Brazil and Billing with Canada
    browser.fill("shipping-city", customer_city2)
    browser.select("shipping-country", customer_country2)
    wait_until_appeared(browser, "select[name='shipping-region_code']")
    browser.select("shipping-region_code", customer_region2)

    browser.fill("billing-city", customer_city3)
    browser.select("billing-country", customer_country3)
    wait_until_appeared(browser, "select[name='billing-region_code']")
    browser.select("billing-region_code", customer_region3)

    # continue
    click_element(browser, "#addresses button[type='submit']")
    wait_until_condition(
        browser, lambda x: x.is_text_present("Checkout: Shipping & Payment"))

    click_element(browser, ".btn.btn-primary.btn-lg.pull-right"
                  )  # click "continue" on methods page
    wait_until_condition(browser, lambda x: x.is_text_present(
        "Checkout: Confirmation"))  # we are indeed in confirmation page

    # See that all expected texts are present
    wait_until_condition(browser, lambda x: x.is_text_present(product_name))
    wait_until_condition(browser, lambda x: x.is_text_present(sm.name))
    wait_until_condition(browser, lambda x: x.is_text_present(pm.name))
    wait_until_condition(browser, lambda x: x.is_text_present("Delivery"))
    wait_until_condition(browser, lambda x: x.is_text_present("Billing"))
    # check that user information is available
    wait_until_condition(browser, lambda x: x.is_text_present(customer_name))
    wait_until_condition(browser, lambda x: x.is_text_present(customer_street))
    wait_until_condition(browser, lambda x: x.is_text_present(customer_city2))
    wait_until_condition(browser, lambda x: x.is_text_present(customer_city3))
    wait_until_condition(browser, lambda x: x.is_text_present("Canada"))
    wait_until_condition(browser, lambda x: x.is_text_present("Brazil"))

    browser.execute_script(
        'document.getElementById("id_accept_terms").checked=true'
    )  # click accept terms
    click_element(browser, ".btn.btn-primary.btn-lg")
    wait_until_condition(
        browser, lambda x: x.is_text_present("Thank you for your order!"))
예제 #41
0
def test_browser_checkout_addresses_vertical(browser, live_server, settings):
    with override_settings(SHUUP_CHECKOUT_VIEW_SPEC=(
            "shuup.front.views.checkout:SinglePageCheckoutView")):
        # initialize
        product_name = "Test Product"
        get_default_shop()
        pm = get_default_payment_method()
        sm = get_default_shipping_method()
        product = create_orderable_product(product_name, "test-123", price=100)
        OrderStatus.objects.create(identifier="initial",
                                   role=OrderStatusRole.INITIAL,
                                   name="initial",
                                   default=True)

        # initialize test and go to front page
        browser = initialize_front_browser_test(browser, live_server)
        # check that front page actually loaded
        wait_until_condition(
            browser, lambda x: x.is_text_present("Welcome to Default!"))
        wait_until_condition(browser,
                             lambda x: x.is_text_present("Newest Products"))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(product_name))

        click_element(browser, "#product-%s" %
                      product.pk)  # open product from product list
        click_element(browser, "#add-to-cart-button-%s" %
                      product.pk)  # add product to basket

        wait_until_appeared(browser, ".cover-wrap")
        wait_until_disappeared(browser, ".cover-wrap")

        click_element(
            browser,
            "#navigation-basket-partial")  # open upper basket navigation menu
        click_element(
            browser,
            "a[href='/basket/']")  # click the link to basket in dropdown
        wait_until_condition(browser, lambda x: x.is_text_present(
            "Shopping cart"))  # we are in basket page
        wait_until_condition(
            browser,
            lambda x: x.is_text_present(product_name))  # product is in basket

        click_element(
            browser,
            "a[href='/checkout/']")  # click link that leads to checkout
        wait_until_appeared(browser, "h4.panel-title")

        customer_name = "Test Tester"
        customer_street = "Test Street"

        customer_city1 = "Los Angeles"
        customer_city2 = "Chiedo"

        customer_region1 = "CA"
        customer_region2 = "My Region Name"

        customer_country1 = "US"
        customer_country2 = "AR"  # Doesn't have region codes

        # Fill all billing address fields with USA address
        browser.fill("billing-name", customer_name)
        browser.fill("billing-street", customer_street)
        browser.fill("billing-city", customer_city1)
        browser.select("billing-country", customer_country1)
        wait_until_appeared(browser, "select[name='billing-region_code']")
        browser.select("billing-region_code", customer_region1)

        # Click to send to billing address (copy billing to shipping)
        browser.find_by_css("label[for='same_as_billing']").first.click()

        # continue
        click_element(browser, "#addresses button[type='submit']")

        wait_until_condition(browser,
                             lambda x: x.is_text_present("Shipping & Payment"))
        # continue on methods page
        click_element(browser, ".btn.btn-primary.btn-lg.pull-right")
        wait_until_condition(browser,
                             lambda x: x.is_text_present("Confirmation"))

        # See that all expected texts are present
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_name))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_street))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_city1))
        wait_until_condition(browser,
                             lambda x: x.is_text_present("United States"))

        # back to address phase, we want to send to Argentina
        browser.find_by_css("a[data-phase='addresses']").first.click()

        # all values must be there with correct saved values
        billing_country = browser.find_by_name("billing-country").first
        wait_until_appeared(browser, "select[name='billing-region_code']")
        billing_region_code = browser.find_by_name("billing-region_code").first
        shipping_country = browser.find_by_name("shipping-country").first
        wait_until_appeared(browser, "select[name='shipping-region_code']")
        shipping_region_code = browser.find_by_name(
            "shipping-region_code").first
        assert billing_country.value == customer_country1
        assert billing_region_code.value == customer_region1
        assert shipping_country.value == customer_country1
        assert shipping_region_code.value == customer_region1

        # same_as_billing is not checked
        assert not browser.find_by_css(
            "label[for='same_as_billing']").first.checked

        # click on same as billing twice, so we copy and clean the field, just to try messing
        browser.find_by_css("label[for='same_as_billing']").first.click()
        browser.find_by_css("label[for='same_as_billing']").first.click()

        # region field should be enabled
        wait_until_condition(
            browser, lambda x: not x.find_by_name("shipping-region_code").
            has_class("disabled"))

        # Fill all shipping address fields - Argentina address
        browser.fill("shipping-name", customer_name)
        browser.fill("shipping-street", customer_street)
        browser.fill("shipping-city", customer_city2)
        browser.select("shipping-country", customer_country2)
        browser.fill("shipping-region", customer_region2)

        # continue
        click_element(browser, "#addresses button[type='submit']")
        wait_until_condition(browser,
                             lambda x: x.is_text_present("Shipping & Payment"))
        # continue
        click_element(browser, ".btn.btn-primary.btn-lg.pull-right")
        wait_until_condition(browser,
                             lambda x: x.is_text_present("Confirmation"))

        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_name))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_street))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_city1))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_city2))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_region1))
        wait_until_condition(browser,
                             lambda x: x.is_text_present(customer_region2))
        wait_until_condition(browser, lambda x: x.is_text_present("Argentina"))
        wait_until_condition(browser,
                             lambda x: x.is_text_present("United States"))

        browser.execute_script(
            'document.getElementById("id_accept_terms").checked=true'
        )  # click accept terms
        click_element(browser,
                      ".btn.btn-primary.btn-lg")  # click "place order"

        wait_until_condition(browser, lambda x: x.is_text_present(
            "Thank you for your order!"))  # order succeeded
예제 #42
0
def create_order(request, creator, customer, product):
    billing_address = get_address().to_immutable()
    shipping_address = get_address(name="Shippy Doge").to_immutable()
    shipping_address.save()
    default_pm = get_default_payment_method()
    default_sm = get_default_shipping_method()
    shop = request.shop
    order = Order(
        creator=creator,
        customer=customer,
        shop=shop,
        payment_method=default_pm,
        shipping_method=default_sm,
        billing_address=billing_address,
        shipping_address=shipping_address,
        order_date=now(),
        status=get_initial_order_status(),
        currency=shop.currency,
        prices_include_tax=shop.prices_include_tax,
    )
    order.full_clean()
    order.save()
    supplier = get_default_supplier()
    product_order_line = OrderLine(order=order)
    update_order_line_from_product(pricing_context=request,
                                   order_line=product_order_line,
                                   product=product,
                                   quantity=5,
                                   supplier=supplier)

    assert product_order_line.text == product.safe_translation_getter("name")
    product_order_line.base_unit_price = shop.create_price(100)
    assert product_order_line.price.value > 0
    product_order_line.save()

    line_tax = get_line_taxes_for(product_order_line)[0]

    order_line_tax = OrderLineTax.from_tax(
        tax=line_tax.tax,
        base_amount=line_tax.base_amount,
        order_line=product_order_line,
    )
    order_line_tax.save(
    )  # Save order_line_tax before linking to order_line.tax
    product_order_line.taxes.add(order_line_tax)

    discount_order_line = OrderLine(order=order,
                                    quantity=1,
                                    type=OrderLineType.OTHER)
    discount_order_line.discount_amount = shop.create_price(30)
    assert discount_order_line.discount_amount.value == 30
    assert discount_order_line.price.value == -30
    assert discount_order_line.base_unit_price.value == 0
    discount_order_line.save()

    order.cache_prices()
    order.check_all_verified()
    order.save()

    assert not order.can_set_complete()

    base = 5 * shop.create_price(100).amount
    discount = shop.create_price(30).amount
    tax_value = line_tax.amount
    if not order.prices_include_tax:
        assert order.taxless_total_price.amount == base - discount
        assert order.taxful_total_price.amount == base + tax_value - discount
    else:
        assert_almost_equal(order.taxless_total_price.amount,
                            base - tax_value - discount)
        assert_almost_equal(order.taxful_total_price.amount, base - discount)

    assert not order.is_fully_shipped()
    shipment = order.create_shipment_of_all_products(supplier=supplier)
    assert order.is_fully_shipped()

    assert shipment.total_products == 5, "All products were shipped"
    assert shipment.weight == product.gross_weight * 5 / 1000, "Gravity works"
    assert not order.get_unshipped_products(
    ), "Nothing was left in the warehouse"

    assert order.can_set_complete()

    order.create_payment(order.taxful_total_price)
    assert order.is_paid()
    assert Order.objects.paid().filter(
        pk=order.pk).exists(), "It was paid! Honestly!"
    assert order.has_products()

    assert order.get_available_shipping_methods()
    assert order.get_available_payment_methods()

    assert default_sm in order.get_available_shipping_methods()
    assert default_pm in order.get_available_payment_methods()
예제 #43
0
def test_model_form_partially_translated(rf, admin_user):
    with override_settings(
            **{
                "LANGUAGES": (("en", "en"), ("fi", "fi"), ("ja", "ja")),
                "PARLER_DEFAULT_LANGUAGE_CODE": "en"
            }):
        activate("en")
        get_default_shop()
        request = apply_request_middleware(rf.get("/"), user=admin_user)
        test_name_en = "Test shop"
        payment_method = get_default_payment_method()
        payment_method.name = test_name_en
        payment_method.save()

        form = PaymentMethodForm(instance=payment_method,
                                 request=request,
                                 languages=settings.LANGUAGES)
        data = get_form_data(form, prepared=True)
        assert data.get("name__en") == test_name_en
        assert not data.get("name__fi")
        form = PaymentMethodForm(data=data,
                                 instance=payment_method,
                                 request=request,
                                 languages=settings.LANGUAGES)
        form.full_clean()
        assert form.is_valid() and not form.errors
        payment_method = form.save()

        # Add description for Finnish and and name in Finnish should be required
        data["description__fi"] = "Some description"
        form = PaymentMethodForm(data=data,
                                 instance=payment_method,
                                 request=request,
                                 languages=settings.LANGUAGES)
        form.full_clean()
        assert not form.is_valid() and form.errors

        test_name_fi = "Some method name in finnish"
        data["name__fi"] = test_name_fi
        form = PaymentMethodForm(data=data,
                                 instance=payment_method,
                                 request=request,
                                 languages=settings.LANGUAGES)
        form.full_clean()
        assert form.is_valid() and not form.errors
        payment_method = form.save()

        assert payment_method.name == test_name_en, "Object in English"

        activate("fi")
        payment_method.set_current_language("fi")
        assert payment_method.name == test_name_fi, "Object in Finnish"

        activate("ja")
        payment_method.set_current_language("ja")
        assert payment_method.name == test_name_en, "Should fallback to English"

        # Check that no sneaky translations is not created for Japan
        with pytest.raises(ObjectDoesNotExist):
            translation = payment_method.get_translation("ja")
            translation.refresh_from_db(
            )  # Just in case if the translation object comes from cache or something

        # Empty finnish translations and see if Finnish starts fallbacks too
        data["name__fi"] = data["description__fi"] = ""
        form = PaymentMethodForm(data=data,
                                 instance=payment_method,
                                 request=request,
                                 languages=settings.LANGUAGES)
        form.full_clean()
        assert form.is_valid() and not form.errors
        form.save()

        # Check that no sneaky translations is not created for Finnish
        with pytest.raises(ObjectDoesNotExist):
            translation = payment_method.get_translation("fi")
            translation.refresh_from_db(
            )  # Just in case if the translation object comes from cache or something
예제 #44
0
def test_browser_checkout(browser, live_server, settings):
    # initialize
    product_name = "Test Product"
    get_default_shop()
    pm = get_default_payment_method()
    sm = get_default_shipping_method()
    product = create_orderable_product(product_name, "test-123", price=100)
    OrderStatus.objects.create(
        identifier="initial",
        role=OrderStatusRole.INITIAL,
        name="initial",
        default=True
    )

    # initialize test and go to front page
    browser = initialize_front_browser_test(browser, live_server)

    # check that front page actually loaded
    assert browser.is_text_present("Welcome to Default!")
    assert browser.is_text_present("Newest Products")
    assert browser.is_text_present(product_name)

    click_element(browser, "#product-%s" % product.pk)  # open product from product list
    click_element(browser, "#add-to-cart-button-%s" % product.pk)  # add product to basket

    wait_until_appeared(browser, ".cover-wrap")
    wait_until_disappeared(browser, ".cover-wrap")

    click_element(browser, "#navigation-basket-partial")  # open upper basket navigation menu
    click_element(browser, "a[href='/basket/']")  # click the link to basket in dropdown
    assert browser.is_text_present("Shopping cart")  # we are in basket page
    assert browser.is_text_present(product_name)  # product is in basket

    click_element(browser, "a[href='/checkout/']") # click link that leads to checkout

    customer_name = "Test Tester"
    customer_street = "Test Street"
    customer_city = "Test City"
    customer_region = "CA"
    customer_country = "US"

    # Fill all necessary information
    browser.fill("billing-name", customer_name)
    browser.fill("billing-street", customer_street)
    browser.fill("billing-city", customer_city)
    browser.select("billing-country", customer_country)
    wait_until_appeared(browser, "select[name='billing-region_code']")
    browser.select("billing-region_code", customer_region)

    click_element(browser, "#addresses button[type='submit']")

    assert browser.is_text_present("There were errors on submitted form fields. Please check them and try again.")

    # Fill the errors
    browser.fill("shipping-name", customer_name)
    browser.fill("shipping-street", customer_street)
    browser.fill("shipping-city", customer_city)
    browser.select("shipping-country", customer_country)

    click_element(browser, "#addresses button[type='submit']")
    assert browser.is_text_present("Checkout: Shipping & Payment")

    assert browser.is_text_present(sm.name)  # shipping method name is present
    assert browser.is_text_present(pm.name)  # payment method name is present

    click_element(browser, ".btn.btn-primary.btn-lg.pull-right")  # click "continue" on methods page

    assert browser.is_text_present("Checkout: Confirmation")  # we are indeed in confirmation page

    # See that all expected texts are present
    assert browser.is_text_present(product_name)
    assert browser.is_text_present(sm.name)
    assert browser.is_text_present(pm.name)
    assert browser.is_text_present("Delivery")
    assert browser.is_text_present("Billing")

    # check that user information is available
    assert browser.is_text_present(customer_name)
    assert browser.is_text_present(customer_street)
    assert browser.is_text_present(customer_city)
    assert browser.is_text_present("United States")

    browser.execute_script('document.getElementById("id_accept_terms").checked=true')  # click accept terms
    click_element(browser, ".btn.btn-primary.btn-lg")  # click "place order"

    assert browser.is_text_present("Thank you for your order!")  # order succeeded
예제 #45
0
def test_create_order(admin_user, currency):
    create_default_order_statuses()
    shop = get_default_shop()
    shop.currency = currency
    tax = get_default_tax()
    Currency.objects.get_or_create(code=currency, decimal_places=2)
    shop.save()
    sm = get_default_shipping_method()
    pm = get_default_payment_method()
    contact = create_random_person(locale="en_US", minimum_name_comp_len=5)
    product = create_product(sku=printable_gibberish(),
                             supplier=get_default_supplier(),
                             shop=shop)
    assert not Order.objects.count()
    client = _get_client(admin_user)
    lines = [
        {
            "type": "product",
            "product": product.id,
            "quantity": "1",
            "base_unit_price_value": "5.00"
        },
        {
            "type": "product",
            "product": product.id,
            "quantity": "2",
            "base_unit_price_value": "1.00",
            "discount_amount_value": "0.50"
        },
        {
            "type": "other",
            "sku": "hello",
            "text": "A greeting",
            "quantity": 1,
            "base_unit_price_value": "3.5"
        },
        {
            "type": "text",
            "text": "This was an order!",
            "quantity": 0
        },
    ]
    response = client.post("/api/shuup/order/",
                           content_type="application/json",
                           data=json.dumps({
                               "shop": shop.pk,
                               "shipping_method": sm.pk,
                               "payment_method": pm.pk,
                               "customer": contact.pk,
                               "lines": lines
                           }))
    assert response.status_code == 201
    assert Order.objects.count() == 1
    order = Order.objects.first()
    assert order.shop == shop
    assert order.shipping_method == sm
    assert order.payment_method == pm
    assert order.customer == contact
    assert order.creator == admin_user
    assert order.billing_address == contact.default_billing_address.to_immutable(
    )
    assert order.shipping_address == contact.default_shipping_address.to_immutable(
    )
    assert order.payment_status == PaymentStatus.NOT_PAID
    assert order.shipping_status == ShippingStatus.NOT_SHIPPED
    assert order.status == OrderStatus.objects.get_default_initial()
    assert order.taxful_total_price_value == decimal.Decimal(10)
    assert order.lines.count(
    ) == 6  # shipping line, payment line, 2 product lines, 2 other lines
    assert order.currency == currency
    for idx, line in enumerate(order.lines.all()[:4]):
        assert line.quantity == decimal.Decimal(lines[idx].get("quantity"))
        assert line.base_unit_price_value == decimal.Decimal(lines[idx].get(
            "base_unit_price_value", 0))
        assert line.discount_amount_value == decimal.Decimal(lines[idx].get(
            "discount_amount_value", 0))

    # Test tax summary
    response_data = json.loads(response.content.decode("utf-8"))
    # Tax summary should not be present here
    assert "summary" not in response_data

    response = client.get('/api/shuup/order/{}/taxes/'.format(order.pk))
    assert response.status_code == status.HTTP_200_OK
    response_data = json.loads(response.content.decode("utf-8"))

    assert "lines" in response_data
    assert "summary" in response_data
    line_summary = response_data["lines"]
    summary = response_data["summary"]
    first_tax_summary = summary[0]

    assert int(first_tax_summary["tax_id"]) == tax.id
    assert first_tax_summary["tax_rate"] == tax.rate

    first_line_summary = line_summary[0]
    assert "tax" in first_line_summary

    response = client.get("/api/shuup/order/%s/" % order.id)
    assert response.status_code == status.HTTP_200_OK
    order_data = json.loads(response.content.decode("utf-8"))
    assert order_data.get("id") == order.id

    assert "available_shipping_methods" in order_data
    assert "available_payment_methods" in order_data

    assert order_data["available_payment_methods"][0]["id"] == pm.id
    assert order_data["available_shipping_methods"][0]["id"] == sm.id