Test cembra/byjuno invoice
This commit is contained in:
parent
052b07eabf
commit
fab9297989
|
|
@ -1,6 +1,7 @@
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { computed } from "vue";
|
import { computed } from "vue";
|
||||||
import { useEntities } from "@/services/entities";
|
import { useEntities } from "@/services/entities";
|
||||||
|
import { t } from "i18next";
|
||||||
|
|
||||||
const props = defineProps<{
|
const props = defineProps<{
|
||||||
modelValue: {
|
modelValue: {
|
||||||
|
|
@ -11,6 +12,7 @@ const props = defineProps<{
|
||||||
postal_code: string;
|
postal_code: string;
|
||||||
city: string;
|
city: string;
|
||||||
country_code: string;
|
country_code: string;
|
||||||
|
payment_method: string;
|
||||||
|
|
||||||
phone_number: string;
|
phone_number: string;
|
||||||
birth_date: string;
|
birth_date: string;
|
||||||
|
|
@ -21,6 +23,13 @@ const emit = defineEmits(["update:modelValue"]);
|
||||||
|
|
||||||
const { countries } = useEntities();
|
const { countries } = useEntities();
|
||||||
|
|
||||||
|
const paymentMethods = computed(() => {
|
||||||
|
return [
|
||||||
|
{ value: "credit_card", label: t("a.Debit-/Kreditkarte / Twint") },
|
||||||
|
{ value: "cembra_byjuno", label: t("a.Rechnung") },
|
||||||
|
];
|
||||||
|
});
|
||||||
|
|
||||||
const address = computed({
|
const address = computed({
|
||||||
get() {
|
get() {
|
||||||
return props.modelValue;
|
return props.modelValue;
|
||||||
|
|
@ -168,6 +177,35 @@ const address = computed({
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="col-span-full">
|
<div class="col-span-full">
|
||||||
|
<label
|
||||||
|
for="paymentMethod"
|
||||||
|
class="block text-sm font-medium leading-6 text-gray-900"
|
||||||
|
>
|
||||||
|
{{ $t("a.Zahlungsart") }}
|
||||||
|
</label>
|
||||||
|
<div class="mt-2">
|
||||||
|
<select
|
||||||
|
id="paymentMethod"
|
||||||
|
v-model="address.payment_method"
|
||||||
|
required
|
||||||
|
name="paymentMethod"
|
||||||
|
class="block w-full border-0 py-1.5 text-gray-900 ring-1 ring-inset ring-gray-300 focus:ring-2 focus:ring-inset focus:ring-blue-600 sm:text-sm sm:leading-6"
|
||||||
|
>
|
||||||
|
<option v-for="pm in paymentMethods" :key="pm.value" :value="pm.value">
|
||||||
|
{{ pm.label }}
|
||||||
|
</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div v-if="address.payment_method === 'cembra_byjuno'" class="col-span-full">
|
||||||
|
<p class="mt-4">
|
||||||
|
TODO: Eine Zahlung mit Rechnung wird immer auf deine Privatadresse verrechnet.
|
||||||
|
Du musst zwinged deine Telefonnummer und dein Geburtsdatum angeben.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div v-if="address.payment_method === 'cembra_byjuno'" class="col-span-full">
|
||||||
<label for="phone" class="block text-sm font-medium leading-6 text-gray-900">
|
<label for="phone" class="block text-sm font-medium leading-6 text-gray-900">
|
||||||
{{ $t("a.Telefonnummer") }}
|
{{ $t("a.Telefonnummer") }}
|
||||||
</label>
|
</label>
|
||||||
|
|
@ -183,7 +221,7 @@ const address = computed({
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="col-span-full">
|
<div v-if="address.payment_method === 'cembra_byjuno'" class="col-span-full">
|
||||||
<label for="birth-date" class="block text-sm font-medium leading-6 text-gray-900">
|
<label for="birth-date" class="block text-sm font-medium leading-6 text-gray-900">
|
||||||
{{ $t("a.Geburtsdatum") }}
|
{{ $t("a.Geburtsdatum") }}
|
||||||
</label>
|
</label>
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import WizardPage from "@/components/onboarding/WizardPage.vue";
|
import WizardPage from "@/components/onboarding/WizardPage.vue";
|
||||||
import { computed, ref } from "vue";
|
import { computed, ref, watch } from "vue";
|
||||||
import { type User, useUserStore } from "@/stores/user";
|
import { type User, useUserStore } from "@/stores/user";
|
||||||
import PersonalAddress from "@/components/onboarding/PersonalAddress.vue";
|
import PersonalAddress from "@/components/onboarding/PersonalAddress.vue";
|
||||||
import OrganisationAddress from "@/components/onboarding/OrganisationAddress.vue";
|
import OrganisationAddress from "@/components/onboarding/OrganisationAddress.vue";
|
||||||
|
|
@ -56,6 +56,8 @@ const address = ref({
|
||||||
city: user.city,
|
city: user.city,
|
||||||
country_code: user.country?.country_code ?? "CH",
|
country_code: user.country?.country_code ?? "CH",
|
||||||
|
|
||||||
|
payment_method: "credit_card",
|
||||||
|
|
||||||
phone_number: user.phone_number,
|
phone_number: user.phone_number,
|
||||||
birth_date: user.birth_date,
|
birth_date: user.birth_date,
|
||||||
|
|
||||||
|
|
@ -75,14 +77,14 @@ const setWithCompanyAddress = (value: boolean) => {
|
||||||
address.value.invoice_address = value ? "org" : "prv";
|
address.value.invoice_address = value ? "org" : "prv";
|
||||||
};
|
};
|
||||||
|
|
||||||
const withCembraInvoice = ref<boolean>(false);
|
watch(
|
||||||
|
() => address.value.payment_method,
|
||||||
function toggleCembraInvoice() {
|
(newValue) => {
|
||||||
withCembraInvoice.value = !withCembraInvoice.value;
|
if (newValue === "cembra_byjuno") {
|
||||||
if (!withCembraInvoice.value) {
|
setWithCompanyAddress(false);
|
||||||
setWithCompanyAddress(false);
|
}
|
||||||
}
|
}
|
||||||
}
|
);
|
||||||
|
|
||||||
type FormErrors = {
|
type FormErrors = {
|
||||||
personal: string[];
|
personal: string[];
|
||||||
|
|
@ -136,7 +138,7 @@ function validateAddress() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (withCembraInvoice.value) {
|
if (address.value.payment_method === "cembra_byjuno") {
|
||||||
if (!address.value.phone_number) {
|
if (!address.value.phone_number) {
|
||||||
formErrors.value.personal.push(t("a.Telefonnummer"));
|
formErrors.value.personal.push(t("a.Telefonnummer"));
|
||||||
}
|
}
|
||||||
|
|
@ -211,11 +213,14 @@ const executePayment = async () => {
|
||||||
address.value.phone_number = normalizeSwissPhoneNumber(address.value.phone_number);
|
address.value.phone_number = normalizeSwissPhoneNumber(address.value.phone_number);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const addressData = Object.assign({}, address.value);
|
||||||
|
delete addressData.payment_method;
|
||||||
|
|
||||||
itPost("/api/shop/vv/checkout/", {
|
itPost("/api/shop/vv/checkout/", {
|
||||||
redirect_url: fullHost,
|
redirect_url: fullHost,
|
||||||
address: address.value,
|
address: addressData,
|
||||||
product: props.courseType,
|
product: props.courseType,
|
||||||
with_cembra_invoice: withCembraInvoice.value,
|
with_cembra_byjuno_invoice: address.value.payment_method === "cembra_byjuno",
|
||||||
device_fingerprint_session_key: getLocalSessionKey(),
|
device_fingerprint_session_key: getLocalSessionKey(),
|
||||||
}).then((res: any) => {
|
}).then((res: any) => {
|
||||||
console.log("Going to next page", res.next_step_url);
|
console.log("Going to next page", res.next_step_url);
|
||||||
|
|
@ -227,7 +232,9 @@ const executePayment = async () => {
|
||||||
<template>
|
<template>
|
||||||
<WizardPage :step="2">
|
<WizardPage :step="2">
|
||||||
<template #content>
|
<template #content>
|
||||||
<DatatransCembraDeviceFingerprint v-if="withCembraInvoice" />
|
<DatatransCembraDeviceFingerprint
|
||||||
|
v-if="address.payment_method === 'cembra_byjuno'"
|
||||||
|
/>
|
||||||
<h2 class="my-10" data-cy="account-checkout-title">
|
<h2 class="my-10" data-cy="account-checkout-title">
|
||||||
{{ $t("a.Lehrgang kaufen") }}
|
{{ $t("a.Lehrgang kaufen") }}
|
||||||
</h2>
|
</h2>
|
||||||
|
|
@ -281,24 +288,7 @@ const executePayment = async () => {
|
||||||
{{ formErrors.personal.join(", ") }}
|
{{ formErrors.personal.join(", ") }}
|
||||||
</p>
|
</p>
|
||||||
|
|
||||||
<div class="flex flex-row items-center space-x-2 text-sm">
|
<section v-if="address.payment_method !== 'cembra_byjuno'">
|
||||||
<ItToggleSwitch
|
|
||||||
data-cy="cembra-switch"
|
|
||||||
:initially-switched-left="withCembraInvoice"
|
|
||||||
@click="toggleCembraInvoice()"
|
|
||||||
></ItToggleSwitch>
|
|
||||||
<span :class="{ 'text-gray-700': !withCembraInvoice }">
|
|
||||||
"TODO: Zahlung auf Rechnung/Cembra"
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<section v-if="withCembraInvoice">
|
|
||||||
<p class="mt-4">
|
|
||||||
TODO: Bei Zahlung auf Rechnung/Cembra, wird immer auf deine Privatadresse
|
|
||||||
verrechnet. Du musst zwinged deine Telefonnummer und Geburtsdatum angeben.
|
|
||||||
</p>
|
|
||||||
</section>
|
|
||||||
<section v-else>
|
|
||||||
<div class="mt-4">
|
<div class="mt-4">
|
||||||
<button
|
<button
|
||||||
v-if="!withCompanyAddress"
|
v-if="!withCompanyAddress"
|
||||||
|
|
@ -362,7 +352,9 @@ const executePayment = async () => {
|
||||||
data-cy="continue-pay"
|
data-cy="continue-pay"
|
||||||
@click="executePayment"
|
@click="executePayment"
|
||||||
>
|
>
|
||||||
<template v-if="withCembraInvoice">TODO: Mit Rechnung/Cembra bezahlen</template>
|
<template v-if="address.payment_method === 'cembra_byjuno'">
|
||||||
|
{{ $t("a.Mit Rechnung bezahlen") }}
|
||||||
|
</template>
|
||||||
<template v-else>
|
<template v-else>
|
||||||
{{ $t("a.Mit Kreditkarte bezahlen") }}
|
{{ $t("a.Mit Kreditkarte bezahlen") }}
|
||||||
</template>
|
</template>
|
||||||
|
|
|
||||||
|
|
@ -119,7 +119,8 @@ describe("checkout.cy.js", () => {
|
||||||
"contain",
|
"contain",
|
||||||
"Lehrgang kaufen"
|
"Lehrgang kaufen"
|
||||||
);
|
);
|
||||||
cy.get('[data-cy="cembra-switch"]').click();
|
|
||||||
|
cy.get('#paymentMethod').select('cembra_byjuno');
|
||||||
|
|
||||||
cy.get("#street-address").type("Eggersmatt");
|
cy.get("#street-address").type("Eggersmatt");
|
||||||
cy.get("#street-number").type("32");
|
cy.get("#street-number").type("32");
|
||||||
|
|
@ -169,7 +170,7 @@ describe("checkout.cy.js", () => {
|
||||||
expect(ci.country).to.equal("CH");
|
expect(ci.country).to.equal("CH");
|
||||||
expect(ci.phone_number).to.equal("+41792018586");
|
expect(ci.phone_number).to.equal("+41792018586");
|
||||||
expect(ci.birth_date).to.equal("1982-06-09");
|
expect(ci.birth_date).to.equal("1982-06-09");
|
||||||
expect(ci.cembra_invoice).to.be.true;
|
expect(ci.cembra_byjuno_invoice).to.be.true;
|
||||||
|
|
||||||
expect(ci.invoice_address).to.equal("prv");
|
expect(ci.invoice_address).to.equal("prv");
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -16,7 +16,7 @@ class Migration(migrations.Migration):
|
||||||
),
|
),
|
||||||
migrations.AddField(
|
migrations.AddField(
|
||||||
model_name="checkoutinformation",
|
model_name="checkoutinformation",
|
||||||
name="cembra_invoice",
|
name="cembra_byjuno_invoice",
|
||||||
field=models.BooleanField(default=False),
|
field=models.BooleanField(default=False),
|
||||||
),
|
),
|
||||||
migrations.AddField(
|
migrations.AddField(
|
||||||
|
|
|
||||||
|
|
@ -79,7 +79,7 @@ class CheckoutInformation(models.Model):
|
||||||
)
|
)
|
||||||
|
|
||||||
# optional fields for cembra payment
|
# optional fields for cembra payment
|
||||||
cembra_invoice = models.BooleanField(default=False)
|
cembra_byjuno_invoice = models.BooleanField(default=False)
|
||||||
birth_date = models.DateField(null=True, blank=True)
|
birth_date = models.DateField(null=True, blank=True)
|
||||||
phone_number = models.CharField(max_length=255, blank=True, default="")
|
phone_number = models.CharField(max_length=255, blank=True, default="")
|
||||||
email = models.CharField(max_length=255, blank=True, default="")
|
email = models.CharField(max_length=255, blank=True, default="")
|
||||||
|
|
|
||||||
|
|
@ -80,6 +80,7 @@ def init_datatrans_transaction(
|
||||||
datatrans_customer_data: dict = None,
|
datatrans_customer_data: dict = None,
|
||||||
datatrans_int_data: dict = None,
|
datatrans_int_data: dict = None,
|
||||||
context_data: dict = None,
|
context_data: dict = None,
|
||||||
|
with_cembra_byjuno_invoice: bool = False,
|
||||||
):
|
):
|
||||||
payload = {
|
payload = {
|
||||||
# We use autoSettle=True, so that we don't have to settle the transaction:
|
# We use autoSettle=True, so that we don't have to settle the transaction:
|
||||||
|
|
@ -97,6 +98,9 @@ def init_datatrans_transaction(
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# FIXME: test with working cembra byjuno invoice customer?
|
||||||
|
# if with_cembra_byjuno_invoice:
|
||||||
|
# payload["paymentMethods"] = ["INT"]
|
||||||
if datatrans_customer_data:
|
if datatrans_customer_data:
|
||||||
payload["customer"] = datatrans_customer_data
|
payload["customer"] = datatrans_customer_data
|
||||||
if datatrans_int_data:
|
if datatrans_int_data:
|
||||||
|
|
|
||||||
|
|
@ -111,14 +111,14 @@ def checkout_vv(request):
|
||||||
if checkouts.filter(state=CheckoutState.PAID).exists():
|
if checkouts.filter(state=CheckoutState.PAID).exists():
|
||||||
return next_step_response(url="/")
|
return next_step_response(url="/")
|
||||||
|
|
||||||
with_cembra_invoice = request.data.get("with_cembra_invoice", False)
|
with_cembra_byjuno_invoice = request.data.get("with_cembra_byjuno_invoice", False)
|
||||||
ip_address = request.META.get("REMOTE_ADDR")
|
ip_address = request.META.get("REMOTE_ADDR")
|
||||||
email = request.user.email
|
email = request.user.email
|
||||||
|
|
||||||
try:
|
try:
|
||||||
datatrans_customer_data = None
|
datatrans_customer_data = None
|
||||||
datatrans_int_data = None
|
datatrans_int_data = None
|
||||||
if with_cembra_invoice:
|
if with_cembra_byjuno_invoice:
|
||||||
if "fakeapi" not in settings.DATATRANS_API_ENDPOINT:
|
if "fakeapi" not in settings.DATATRANS_API_ENDPOINT:
|
||||||
request.user.set_increment_abacus_debitor_number()
|
request.user.set_increment_abacus_debitor_number()
|
||||||
|
|
||||||
|
|
@ -158,6 +158,7 @@ def checkout_vv(request):
|
||||||
datatrans_customer_data=datatrans_customer_data,
|
datatrans_customer_data=datatrans_customer_data,
|
||||||
datatrans_int_data=datatrans_int_data,
|
datatrans_int_data=datatrans_int_data,
|
||||||
context_data=context_data,
|
context_data=context_data,
|
||||||
|
with_cembra_byjuno_invoice=with_cembra_byjuno_invoice,
|
||||||
)
|
)
|
||||||
except InitTransactionException as e:
|
except InitTransactionException as e:
|
||||||
if not settings.DEBUG:
|
if not settings.DEBUG:
|
||||||
|
|
@ -193,7 +194,7 @@ def checkout_vv(request):
|
||||||
product_description=product.description,
|
product_description=product.description,
|
||||||
email=email,
|
email=email,
|
||||||
ip_address=ip_address,
|
ip_address=ip_address,
|
||||||
cembra_invoice=with_cembra_invoice,
|
cembra_byjuno_invoice=with_cembra_byjuno_invoice,
|
||||||
device_fingerprint_session_key=request.data.get(
|
device_fingerprint_session_key=request.data.get(
|
||||||
"device_fingerprint_session_key", ""
|
"device_fingerprint_session_key", ""
|
||||||
),
|
),
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue