diff --git a/app/app.vue b/app/app.vue index 988b270..a82fd95 100644 --- a/app/app.vue +++ b/app/app.vue @@ -10,13 +10,81 @@
@@ -32,13 +100,69 @@
+ + + + @@ -118,10 +275,22 @@ diff --git a/app/components/MachinePrintSelectionModal.vue b/app/components/MachinePrintSelectionModal.vue new file mode 100644 index 0000000..70968c0 --- /dev/null +++ b/app/components/MachinePrintSelectionModal.vue @@ -0,0 +1,136 @@ + + + diff --git a/app/components/MachinePrintSelectionNode.vue b/app/components/MachinePrintSelectionNode.vue new file mode 100644 index 0000000..397b3c5 --- /dev/null +++ b/app/components/MachinePrintSelectionNode.vue @@ -0,0 +1,63 @@ + + + diff --git a/app/components/PageHero.vue b/app/components/PageHero.vue new file mode 100644 index 0000000..342827e --- /dev/null +++ b/app/components/PageHero.vue @@ -0,0 +1,79 @@ + + + diff --git a/app/components/TypeEditActionsBar.vue b/app/components/TypeEditActionsBar.vue new file mode 100644 index 0000000..dfa6b92 --- /dev/null +++ b/app/components/TypeEditActionsBar.vue @@ -0,0 +1,37 @@ + + + diff --git a/app/components/TypeEditBaseInfoSection.vue b/app/components/TypeEditBaseInfoSection.vue new file mode 100644 index 0000000..8ef6c86 --- /dev/null +++ b/app/components/TypeEditBaseInfoSection.vue @@ -0,0 +1,103 @@ + + + diff --git a/app/components/TypeEditComponentsSection.vue b/app/components/TypeEditComponentsSection.vue new file mode 100644 index 0000000..f5a3d50 --- /dev/null +++ b/app/components/TypeEditComponentsSection.vue @@ -0,0 +1,294 @@ + + + diff --git a/app/components/TypeEditCustomFieldsSection.vue b/app/components/TypeEditCustomFieldsSection.vue new file mode 100644 index 0000000..75df437 --- /dev/null +++ b/app/components/TypeEditCustomFieldsSection.vue @@ -0,0 +1,263 @@ + + + diff --git a/app/components/TypeEditForm.vue b/app/components/TypeEditForm.vue index 6d8d7dd..274fd54 100644 --- a/app/components/TypeEditForm.vue +++ b/app/components/TypeEditForm.vue @@ -1,1430 +1,136 @@ diff --git a/app/components/TypeEditMachinePiecesSection.vue b/app/components/TypeEditMachinePiecesSection.vue new file mode 100644 index 0000000..8ffafa8 --- /dev/null +++ b/app/components/TypeEditMachinePiecesSection.vue @@ -0,0 +1,78 @@ + + + diff --git a/app/components/TypeEditToolbar.vue b/app/components/TypeEditToolbar.vue new file mode 100644 index 0000000..ab15cff --- /dev/null +++ b/app/components/TypeEditToolbar.vue @@ -0,0 +1,34 @@ + + + diff --git a/app/components/TypeMachinePieceForm.vue b/app/components/TypeMachinePieceForm.vue index 3832b37..2f4c197 100644 --- a/app/components/TypeMachinePieceForm.vue +++ b/app/components/TypeMachinePieceForm.vue @@ -89,11 +89,10 @@ -
@@ -235,22 +234,44 @@ diff --git a/app/composables/useProfileSession.js b/app/composables/useProfileSession.js new file mode 100644 index 0000000..0e3f44d --- /dev/null +++ b/app/composables/useProfileSession.js @@ -0,0 +1,81 @@ +import { useState, useRequestHeaders, useRuntimeConfig } from '#imports' + +const buildUrl = (path) => { + const config = useRuntimeConfig() + const base = config.public.apiBaseUrl?.replace(/\/$/, '') || '' + return `${base}${path}` +} + +export function useProfileSession() { + const activeProfile = useState('profileSession:active', () => null) + const sessionLoaded = useState('profileSession:loaded', () => false) + const loading = useState('profileSession:loading', () => false) + + const getSessionHeaders = () => { + if (!process.server) return undefined + const headers = useRequestHeaders(['cookie']) + return headers?.cookie ? { cookie: headers.cookie } : undefined + } + + const fetchCurrentProfile = async () => { + loading.value = true + try { + activeProfile.value = await $fetch(buildUrl('/session/profile'), { + method: 'GET', + credentials: 'include', + headers: getSessionHeaders(), + }) + } catch (error) { + if (error?.status === 401) { + activeProfile.value = null + } else { + console.error('Erreur lors du chargement du profil actif', error) + activeProfile.value = null + } + } finally { + sessionLoaded.value = true + loading.value = false + } + return activeProfile.value + } + + const ensureSession = () => { + if (!sessionLoaded.value) { + return fetchCurrentProfile() + } + return Promise.resolve(activeProfile.value) + } + + const activateProfile = async (profileId) => { + await $fetch(buildUrl('/session/profile'), { + method: 'POST', + credentials: 'include', + body: { profileId }, + headers: getSessionHeaders(), + }) + await fetchCurrentProfile() + } + + const logout = async () => { + try { + await $fetch(buildUrl('/session/profile'), { + method: 'DELETE', + credentials: 'include', + headers: getSessionHeaders(), + }) + } finally { + activeProfile.value = null + sessionLoaded.value = true + } + } + + return { + activeProfile, + loading, + sessionLoaded, + ensureSession, + fetchCurrentProfile, + activateProfile, + logout, + } +} diff --git a/app/composables/useProfiles.js b/app/composables/useProfiles.js new file mode 100644 index 0000000..ed2310f --- /dev/null +++ b/app/composables/useProfiles.js @@ -0,0 +1,67 @@ +import { useState, useRequestHeaders, useRuntimeConfig } from '#imports' + +const buildUrl = (path) => { + const config = useRuntimeConfig() + const base = config.public.apiBaseUrl?.replace(/\/$/, '') || '' + return `${base}${path}` +} + +export function useProfiles() { + const profiles = useState('profiles:list', () => []) + const loadingProfiles = useState('profiles:loading', () => false) + const profilesLoaded = useState('profiles:loaded', () => false) + + const getSessionHeaders = () => { + if (!process.server) return undefined + const headers = useRequestHeaders(['cookie']) + return headers?.cookie ? { cookie: headers.cookie } : undefined + } + + const fetchProfiles = async () => { + loadingProfiles.value = true + try { + profiles.value = await $fetch(buildUrl('/profiles'), { + method: 'GET', + credentials: 'include', + headers: getSessionHeaders(), + }) + profilesLoaded.value = true + } catch (error) { + console.error('Erreur lors du chargement des profils', error) + profiles.value = [] + profilesLoaded.value = false + } finally { + loadingProfiles.value = false + } + return profiles.value + } + + const createProfile = async ({ firstName, lastName }) => { + const profile = await $fetch(buildUrl('/profiles'), { + method: 'POST', + credentials: 'include', + body: { firstName, lastName }, + headers: getSessionHeaders(), + }) + await fetchProfiles() + return profile + } + + const deleteProfile = async (profileId) => { + await $fetch(buildUrl(`/profiles/${profileId}`), { + method: 'DELETE', + credentials: 'include', + headers: getSessionHeaders(), + }) + await fetchProfiles() + } + + return { + profiles, + loadingProfiles, + profilesLoaded, + fetchProfiles, + createProfile, + deleteProfile, + } +} diff --git a/app/middleware/profile.global.ts b/app/middleware/profile.global.ts new file mode 100644 index 0000000..32b36a5 --- /dev/null +++ b/app/middleware/profile.global.ts @@ -0,0 +1,12 @@ +import { useProfileSession } from '#imports' + +export default defineNuxtRouteMiddleware(async (to) => { + const { ensureSession, activeProfile } = useProfileSession() + await ensureSession() + + const isProfilesRoute = to.path.startsWith('/profiles') + + if (!activeProfile.value && !isProfilesRoute) { + return navigateTo('/profiles') + } +}) diff --git a/app/pages/documents.vue b/app/pages/documents.vue index ebc4c52..75ba4f5 100644 --- a/app/pages/documents.vue +++ b/app/pages/documents.vue @@ -1,15 +1,9 @@ diff --git a/app/pages/type/[id].vue b/app/pages/type/[id].vue index 8934f37..fddca42 100644 --- a/app/pages/type/[id].vue +++ b/app/pages/type/[id].vue @@ -1,16 +1,14 @@