Add basic registration flow

This commit is contained in:
Christian Cueni 2020-02-05 14:45:10 +01:00
parent 057e65a82f
commit 1d50287dbf
5 changed files with 179 additions and 54 deletions

View File

@ -0,0 +1,11 @@
import * as axios from 'axios'
const hepBaseUrl = 'https://stage.hep-verlag.ch';
export function register(registrationData) {
return axios.post(`${hepBaseUrl}/rest/deutsch/V1/customers`, registrationData);
}
export function login(username, password) {
return axios.post(`${hepBaseUrl}/rest/deutsch/V1/customers`, {username, password});
}

View File

@ -11,7 +11,7 @@ import store from '@/store/index'
import VueScrollTo from 'vue-scrollto'; import VueScrollTo from 'vue-scrollto';
import VueAnalytics from 'vue-analytics'; import VueAnalytics from 'vue-analytics';
import {Validator, install as VeeValidate} from 'vee-validate/dist/vee-validate.minimal.esm.js'; import {Validator, install as VeeValidate} from 'vee-validate/dist/vee-validate.minimal.esm.js';
import {required, min} from 'vee-validate/dist/rules.esm.js'; import {required, min, decimal} from 'vee-validate/dist/rules.esm.js';
import veeDe from 'vee-validate/dist/locale/de'; import veeDe from 'vee-validate/dist/locale/de';
import {dateFilter} from './filters/date-filter'; import {dateFilter} from './filters/date-filter';
import autoGrow from '@/directives/auto-grow' import autoGrow from '@/directives/auto-grow'
@ -76,6 +76,7 @@ const apolloProvider = new VueApollo({
Validator.extend('required', required); Validator.extend('required', required);
Validator.extend('min', min); Validator.extend('min', min);
Validator.extend('decimal', decimal);
const dict = { const dict = {
custom: { custom: {
@ -91,6 +92,7 @@ const dict = {
Validator.localize('de', veeDe) Validator.localize('de', veeDe)
Validator.localize('de', dict) Validator.localize('de', dict)
// https://github.com/baianat/vee-validate/issues/51 // https://github.com/baianat/vee-validate/issues/51
Validator.extend('strongPassword', { Validator.extend('strongPassword', {
getMessage: field => 'Das Passwort muss Grossbuchstaben, Zahlen und Sonderzeichen beinhalten', getMessage: field => 'Das Passwort muss Grossbuchstaben, Zahlen und Sonderzeichen beinhalten',

View File

@ -0,0 +1,23 @@
<template>
<div class="check-email">
<main class="check-email__content">
Ein Email ist auf dem Weg, bitte überprüfen sie ihre E-mail Konto.
</main>
</div>
</template>
<script>
export default {
components: {
}
}
</script>
<style scoped lang="scss">
@import "@/styles/_mixins.scss";
</style>

View File

@ -2,6 +2,23 @@
<div class="registration public-page"> <div class="registration public-page">
<h1 class="registration__title public-page__title">Registrieren Sie ihr persönliches Konto.</h1> <h1 class="registration__title public-page__title">Registrieren Sie ihr persönliches Konto.</h1>
<form class="registration__form registration-form" novalidate @submit.prevent="validateBeforeSubmit"> <form class="registration__form registration-form" novalidate @submit.prevent="validateBeforeSubmit">
<div class="registration-form__field skillboxform-input">
<label for="prefix" class="skillboxform-input__label">Anrede</label>
<select
id="prefix"
name="prefix"
v-model="prefix"
data-vv-as="Prefix"
v-validate="'required'"
:class="{ 'skillboxform-input__input--error': errors.has('prefix') }"
class="change-form__prefix skillbox-input skillboxform-input__input skillbox-dropdown"
autocomplete="off"
data-cy="prefix-input"
>
<option>Herr</option>
<option>Frau</option>
</select>
</div>
<div class="registration-form__field skillboxform-input"> <div class="registration-form__field skillboxform-input">
<label for="firstname" class="skillboxform-input__label">Vorname</label> <label for="firstname" class="skillboxform-input__label">Vorname</label>
<input <input
@ -59,7 +76,7 @@
<input <input
id="email" id="email"
name="email" name="email"
type="text" type="email"
v-model="email" v-model="email"
data-vv-as="E-Mail" data-vv-as="E-Mail"
v-validate="'required|email'" v-validate="'required|email'"
@ -81,29 +98,81 @@
>{{ error }}</small> >{{ error }}</small>
</div> </div>
<div class="change-form__field skillboxform-input"> <div class="change-form__field skillboxform-input">
<label for="licenseKey" class="skillboxform-input__label">Lizenz</label> <label for="address" class="skillboxform-input__label">Adresse</label>
<input <input
id="licenseKey" id="address"
name="licenseKey" name="address"
type="text" type="text"
v-model="licenseKey" v-model="address"
data-vv-as="Lizenz" data-vv-as="Adresse"
v-validate="'required'" v-validate="'required'"
:class="{ 'skillboxform-input__input--error': errors.has('licenseKey') }" :class="{ 'skillboxform-input__input--error': errors.has('address') }"
class="change-form__new skillbox-input skillboxform-input__input" class="change-form__new skillbox-input skillboxform-input__input"
autocomplete="off" autocomplete="off"
data-cy="licenseKey-input" data-cy="address-input"
/> />
<small <small
v-if="errors.has('licenseKey') && submitted" v-if="errors.has('address') && submitted"
class="skillboxform-input__error" class="skillboxform-input__error"
data-cy="licenseKey-local-errors" data-cy="address-local-errors"
>{{ errors.first('licenseKey') }}</small> >{{ errors.first('address') }}</small>
<small <small
v-for="error in licenseKeyErrors" v-for="error in addressErrors"
:key="error" :key="error"
class="skillboxform-input__error" class="skillboxform-input__error"
data-cy="licenseKey-remote-errors" data-cy="address-remote-errors"
>{{ error }}</small>
</div>
<div class="change-form__field skillboxform-input">
<label for="zipCode" class="skillboxform-input__label">PLZ</label>
<input
id="zipCode"
name="zipCode"
type="number"
v-model="zipCode"
data-vv-as="PLZ"
v-validate="'required'"
:class="{ 'skillboxform-input__input--error': errors.has('zipCode') }"
class="change-form__new skillbox-input skillboxform-input__input"
autocomplete="off"
data-cy="zipCode-input"
/>
<small
v-if="errors.has('zipCode') && submitted"
class="skillboxform-input__error"
data-cy="zipCode-local-errors"
>{{ errors.first('zipCode') }}</small>
<small
v-for="error in zipCodeErrors"
:key="error"
class="skillboxform-input__error"
data-cy="zipCode-remote-errors"
>{{ error }}</small>
</div>
<div class="change-form__field skillboxform-input">
<label for="city" class="skillboxform-input__label">Ort</label>
<input
id="city"
name="city"
type="text"
v-model="city"
data-vv-as="Ort"
v-validate="'required'"
:class="{ 'skillboxform-input__input--error': errors.has('city') }"
class="change-form__new skillbox-input skillboxform-input__input"
autocomplete="off"
data-cy="city-input"
/>
<small
v-if="errors.has('city') && submitted"
class="skillboxform-input__error"
data-cy="city-local-errors"
>{{ errors.first('city') }}</small>
<small
v-for="error in cityErrors"
:key="error"
class="skillboxform-input__error"
data-cy="city-remote-errors"
>{{ error }}</small> >{{ error }}</small>
</div> </div>
<div class="skillboxform-input"> <div class="skillboxform-input">
@ -122,7 +191,8 @@
</template> </template>
<script> <script>
import REGISTRATION_MUTATION from '@/graphql/gql/mutations/registration.gql';
import {register} from '../hep-client/index'
export default { export default {
components: {}, components: {},
@ -131,54 +201,58 @@ export default {
validateBeforeSubmit() { validateBeforeSubmit() {
this.$validator.validate().then(result => { this.$validator.validate().then(result => {
this.submitted = true; this.submitted = true;
let that = this;
if (result) { if (result) {
this.$apollo.mutate({ const registrationData = {
client: 'publicClient', customer: {
mutation: REGISTRATION_MUTATION, prefix: this.prefix,
variables: { email: this.email,
input: { firstname: this.firstname,
firstnameInput: this.firstname, lastname: this.lastname,
lastnameInput: this.lastname, gender: this.prefix === 'Herr' ? 1 : 2,
emailInput: this.email, addresses: [{
licenseKeyInput: this.licenseKey, country_id: 'CH',
} street: [this.address],
}, postcode: this.address,
fetchPolicy: 'no-cache' city: this.city,
firstname: this.firstname,
lastname: this.lastname,
default_shipping: true,
default_billing: true
}]
}
};
register(registrationData).then((response) => {
console.log(response)
if (response.data.id && response.data.id > 0) {
this.$router.push({name: 'checkEmail'});
}
}) })
.then(({data: {registration: { success, errors }}}) => { .catch((error) => {
try { if (error.response.data.message && error.response.data.message === 'Ein Kunde mit der gleichen E-Mail-Adresse existiert bereits in einer zugeordneten Website.') {
if (success) { this.emailErrors = ['Die angegebene E-Mail ist bereits registriert.'];
window.location.href = '/registration/set-password/done/'; } else {
} else { this.registrationError = 'Es ist ein Fehler aufgetreten. Bitte versuchen Sie nochmals.';
errors.forEach(function(error) {
switch (error.field) {
case 'email':
that.emailErrors = ['Die angegebene E-Mail ist bereits registriert.'];
break;
case 'license_key':
that.licenseKeyErrors = ['Die angegebenen Lizenz ist unglültig'];
}
})
}
} catch (e) {
console.warn(e);
that.registrationError = 'Es ist ein Fehler aufgetreten. Bitte versuchen Sie nochmals.';
} }
}); });
} }
}); });
}, },
resetForm() { resetForm() {
this.prefix = '';
this.email = ''; this.email = '';
this.lastname = ''; this.lastname = '';
this.firstname = ''; this.firstname = '';
this.licenseKey = ''; this.zipCode = '';
this.firstnameErrors = ''; this.address = '';
this.lastnameErrors = ''; this.city = '';
this.emailErrors = ''; this.firstnameErrors = [];
this.licenseKeyErrors = ''; this.lastnameErrors = [];
this.registrationError = ''; this.emailErrors = [];
this.zipCodeErrors = [];
this.addressErrors = [];
this.cityErrors = [];
this.registrationError = [];
this.submitted = false; this.submitted = false;
this.$validator.reset(); this.$validator.reset();
} }
@ -186,14 +260,19 @@ export default {
data() { data() {
return { return {
prefix: '',
email: '', email: '',
lastname: '', lastname: '',
firstname: '', firstname: '',
licenseKey: '', zipCode: '',
address: '',
city: '',
firstnameErrors: '', firstnameErrors: '',
lastnameErrors: '', lastnameErrors: '',
emailErrors: '', emailErrors: '',
licenseKeyErrors: '', zipCodeErrors: '',
addressErrors: '',
cityErrors: '',
registrationError: '', registrationError: '',
submitted: false submitted: false
}; };

View File

@ -30,6 +30,7 @@ import moduleRoom from '@/pages/moduleRoom'
import login from '@/pages/login' import login from '@/pages/login'
import registration from '@/pages/registration' import registration from '@/pages/registration'
import waitForClass from '@/pages/waitForClass' import waitForClass from '@/pages/waitForClass'
import checkEmail from '@/pages/check-email'
import store from '@/store/index'; import store from '@/store/index';
@ -134,6 +135,15 @@ const routes = [
name: 'noClass', name: 'noClass',
meta: {layout: 'public'} meta: {layout: 'public'}
}, },
{
path: '/check-email',
component: checkEmail,
name: 'checkEmail',
meta: {
public: true,
layout: 'public'
}
},
{path: '/styleguide', component: styleGuidePage}, {path: '/styleguide', component: styleGuidePage},
{path: '*', component: p404} {path: '*', component: p404}
]; ];