|
|
@@ -70,6 +70,16 @@
|
|
|
@submit.prevent="submit"
|
|
|
>
|
|
|
<v-container>
|
|
|
+ <div v-if="isDevelopment" class="dev-tools-container">
|
|
|
+ <v-btn
|
|
|
+ color="info"
|
|
|
+ size="small"
|
|
|
+ prepend-icon="fa fa-magic"
|
|
|
+ @click="fillWithDummyData"
|
|
|
+ >
|
|
|
+ Remplir avec des données de test
|
|
|
+ </v-btn>
|
|
|
+ </div>
|
|
|
<i
|
|
|
>Les champs dont le nom est suivi d'un astérisque (*) sont
|
|
|
obligatoires.</i
|
|
|
@@ -390,11 +400,12 @@ import { useRouter } from 'vue-router'
|
|
|
import type { Ref } from 'vue'
|
|
|
import { reactive } from 'vue'
|
|
|
import _ from 'lodash'
|
|
|
-import { useRuntimeConfig } from '#app'
|
|
|
+import { parsePhoneNumber, isValidPhoneNumber } from 'libphonenumber-js'
|
|
|
+import { useRuntimeConfig, useAsyncData, useNuxtApp } from '#app'
|
|
|
import type { TrialRequest } from '~/types/interface'
|
|
|
import { STRUCTURE_TYPE, LEGAL_STATUS } from '~/types/types'
|
|
|
import { useAp2iRequestService } from '~/composables/data/useAp2iRequestService'
|
|
|
-import { slugify } from '~/utils/string'
|
|
|
+import { slugify } from '~/services/utils/stringUtils'
|
|
|
|
|
|
const router = useRouter()
|
|
|
|
|
|
@@ -418,6 +429,10 @@ const legalStatuses = Object.values(LEGAL_STATUS)
|
|
|
// Get apiRequestService for subdomain availability check
|
|
|
const { ap2iRequestService } = useAp2iRequestService()
|
|
|
|
|
|
+// Check if we're in a development environment
|
|
|
+const config = useRuntimeConfig()
|
|
|
+const isDevelopment = computed(() => config.public.env === 'dev')
|
|
|
+
|
|
|
// Trial request data
|
|
|
const trialRequest = reactive<TrialRequest>({
|
|
|
structureName: '',
|
|
|
@@ -440,6 +455,32 @@ const trialRequest = reactive<TrialRequest>({
|
|
|
newsletterSubscription: false,
|
|
|
})
|
|
|
|
|
|
+// Function to fill the form with dummy data
|
|
|
+const fillWithDummyData = () => {
|
|
|
+ trialRequest.structureName = 'Compagnie Artistique Test'
|
|
|
+ trialRequest.address = '123 Rue des Arts'
|
|
|
+ trialRequest.addressComplement = 'Bâtiment B'
|
|
|
+ trialRequest.postalCode = '75001'
|
|
|
+ trialRequest.city = 'Paris'
|
|
|
+ trialRequest.structureEmail = 'contact@compagnie-test.fr'
|
|
|
+ trialRequest.structureType = 'ARTISTIC_PRACTICE_ONLY'
|
|
|
+ trialRequest.legalStatus = 'ASSOCIATION_LAW_1901'
|
|
|
+ trialRequest.structureIdentifier =
|
|
|
+ 'compagnie-test-' + Math.floor(Math.random() * 1000)
|
|
|
+ trialRequest.siren = '123456789'
|
|
|
+ trialRequest.representativeFirstName = 'Jean'
|
|
|
+ trialRequest.representativeLastName = 'Dupont'
|
|
|
+ trialRequest.representativeFunction = 'Directeur Artistique'
|
|
|
+ trialRequest.representativeEmail = 'jean.dupont@compagnie-test.fr'
|
|
|
+ trialRequest.representativePhone = '0612345678'
|
|
|
+ trialRequest.termsAccepted = true
|
|
|
+ trialRequest.legalRepresentative = true
|
|
|
+ trialRequest.newsletterSubscription = true
|
|
|
+
|
|
|
+ // Trigger subdomain availability check
|
|
|
+ checkSubdomainAvailabilityDebounced()
|
|
|
+}
|
|
|
+
|
|
|
// Track if structure identifier has been manually modified
|
|
|
const structureIdentifierModified = ref(false)
|
|
|
|
|
|
@@ -493,9 +534,14 @@ const validateEmail = (email: string) =>
|
|
|
const validatePostalCode = (postalCode: string) =>
|
|
|
/^\d{5}$/.test(postalCode) || 'Code postal invalide (5 chiffres)'
|
|
|
|
|
|
-const validatePhone = (phone: string) =>
|
|
|
- /^((\+|00)33\s?|0)[1-9]([\s.-]?\d{2}){4}$/.test(phone) ||
|
|
|
- 'Numéro de téléphone invalide'
|
|
|
+const validatePhone = (phone: string) => {
|
|
|
+ try {
|
|
|
+ // Assume French phone number if no country code is provided
|
|
|
+ return isValidPhoneNumber(phone, 'FR') || 'Numéro de téléphone invalide'
|
|
|
+ } catch (error) {
|
|
|
+ return 'Numéro de téléphone invalide'
|
|
|
+ }
|
|
|
+}
|
|
|
|
|
|
const validateSiren = (siren: string) =>
|
|
|
!siren || /^\d{9}$/.test(siren) || 'SIREN invalide (9 chiffres)'
|
|
|
@@ -526,6 +572,21 @@ const validateSubdomainAvailability = (value: string) => {
|
|
|
const trialRequestSent: Ref<boolean> = ref(false)
|
|
|
const errorMsg: Ref<string | null> = ref(null)
|
|
|
|
|
|
+// Function to convert phone number to international format
|
|
|
+const convertToInternationalFormat = (phone: string): string => {
|
|
|
+ try {
|
|
|
+ // Assume French phone number if no country code is provided
|
|
|
+ const phoneNumber = parsePhoneNumber(phone, 'FR')
|
|
|
+ if (phoneNumber && phoneNumber.isValid()) {
|
|
|
+ return phoneNumber.format('E.164') // E.164 format: +33123456789
|
|
|
+ }
|
|
|
+ return phone
|
|
|
+ } catch (error) {
|
|
|
+ console.error('Error converting phone number:', error)
|
|
|
+ return phone
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
// Submit function
|
|
|
const submit = async (): Promise<void> => {
|
|
|
const { valid } = await form.value!.validate()
|
|
|
@@ -534,25 +595,24 @@ const submit = async (): Promise<void> => {
|
|
|
return
|
|
|
}
|
|
|
|
|
|
+ // Convert phone number to international format before submission
|
|
|
+ trialRequest.representativePhone = convertToInternationalFormat(
|
|
|
+ trialRequest.representativePhone
|
|
|
+ )
|
|
|
+
|
|
|
try {
|
|
|
- const config = useRuntimeConfig()
|
|
|
- const apiUrl = `${config.public.apiBaseUrl}/trial/artists_premium`
|
|
|
-
|
|
|
- // Send the data to the API
|
|
|
- const response = await fetch(apiUrl, {
|
|
|
- method: 'POST',
|
|
|
- headers: {
|
|
|
- 'Content-Type': 'application/json',
|
|
|
- },
|
|
|
- body: JSON.stringify(trialRequest),
|
|
|
- })
|
|
|
-
|
|
|
- if (!response.ok) {
|
|
|
- throw new Error(`API request failed with status ${response.status}`)
|
|
|
+ const { data, error } = await useAsyncData('submit-trial-request', () =>
|
|
|
+ ap2iRequestService.post(
|
|
|
+ '/api/public/shop/new-structure-artist-premium-trial-request',
|
|
|
+ trialRequest
|
|
|
+ )
|
|
|
+ )
|
|
|
+
|
|
|
+ if (error.value) {
|
|
|
+ throw error.value
|
|
|
}
|
|
|
|
|
|
- const data = await response.json()
|
|
|
- console.log('Trial request submitted successfully:', data)
|
|
|
+ console.log('Trial request submitted successfully:', data.value)
|
|
|
|
|
|
trialRequestSent.value = true
|
|
|
errorMsg.value = null
|
|
|
@@ -561,8 +621,25 @@ const submit = async (): Promise<void> => {
|
|
|
setTimeout(() => router.push({ path: '', hash: '#anchor' }), 30)
|
|
|
} catch (e) {
|
|
|
console.error('Error submitting trial request:', e)
|
|
|
+
|
|
|
errorMsg.value =
|
|
|
"Une erreur s'est produite lors de l'activation de votre essai. Veuillez réessayer plus tard ou nous contacter directement."
|
|
|
+
|
|
|
+ // Try to extract the specific error message from the API response
|
|
|
+ if (
|
|
|
+ e &&
|
|
|
+ typeof e === 'object' &&
|
|
|
+ 'data' in e &&
|
|
|
+ e.data &&
|
|
|
+ typeof e.data === 'object'
|
|
|
+ ) {
|
|
|
+ const errorData = e.data as { detail?: string }
|
|
|
+ if (errorData.detail) {
|
|
|
+ const { $i18n } = useNuxtApp()
|
|
|
+ // Use translation if available, otherwise use the original message
|
|
|
+ errorMsg.value += '\n' + ($i18n.t(errorData.detail) || errorData.detail)
|
|
|
+ }
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
|
|
|
@@ -698,4 +775,11 @@ h1 {
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+.dev-tools-container {
|
|
|
+ position: absolute;
|
|
|
+ bottom: 10px;
|
|
|
+ right: 10px;
|
|
|
+ z-index: 10;
|
|
|
+}
|
|
|
</style>
|