diff --git a/app/composables/useComposants.ts b/app/composables/useComposants.ts index e9e9bce..be1d070 100644 --- a/app/composables/useComposants.ts +++ b/app/composables/useComposants.ts @@ -4,6 +4,7 @@ import { useApi } from './useApi' import { buildConstructeurRequestPayload, uniqueConstructeurIds } from '~/shared/constructeurUtils' import { useConstructeurs, type Constructeur } from './useConstructeurs' import { extractRelationId, normalizeRelationIds } from '~/shared/apiRelations' +import { extractCollection } from '~/shared/utils/apiHelpers' export interface Composant { id: string @@ -45,23 +46,6 @@ const composants = ref([]) const total = ref(0) const loading = ref(false) -const extractCollection = (payload: unknown): Composant[] => { - if (Array.isArray(payload)) { - return payload as Composant[] - } - const p = payload as Record | null - if (Array.isArray(p?.member)) { - return p.member as Composant[] - } - if (Array.isArray(p?.['hydra:member'])) { - return p['hydra:member'] as Composant[] - } - if (Array.isArray(p?.data)) { - return p.data as Composant[] - } - return [] -} - const extractTotal = (payload: unknown, fallbackLength: number): number => { const p = payload as Record | null if (typeof p?.totalItems === 'number') { diff --git a/app/composables/useConstructeurs.ts b/app/composables/useConstructeurs.ts index 7da2c76..9e4f36c 100644 --- a/app/composables/useConstructeurs.ts +++ b/app/composables/useConstructeurs.ts @@ -1,6 +1,7 @@ import { ref } from 'vue' import { useApi } from './useApi' import { useToast } from './useToast' +import { extractCollection } from '~/shared/utils/apiHelpers' export interface Constructeur { id: string @@ -52,23 +53,6 @@ const upsertConstructeurs = (items: Constructeur[] = []) => { const getIndexedConstructeur = (id: string): Constructeur | null => constructeurs.value.find((item) => item && item.id === id) || null -const extractCollection = (payload: unknown): Constructeur[] => { - if (Array.isArray(payload)) { - return payload as Constructeur[] - } - const p = payload as Record | null - if (Array.isArray(p?.member)) { - return p.member as Constructeur[] - } - if (Array.isArray(p?.['hydra:member'])) { - return p['hydra:member'] as Constructeur[] - } - if (Array.isArray(p?.data)) { - return p.data as Constructeur[] - } - return [] -} - const pendingFetches = new Map>() export function useConstructeurs() { diff --git a/app/composables/useDocuments.ts b/app/composables/useDocuments.ts index c513b12..b34e549 100644 --- a/app/composables/useDocuments.ts +++ b/app/composables/useDocuments.ts @@ -2,6 +2,7 @@ import { ref } from 'vue' import { useApi } from './useApi' import { useToast } from './useToast' import { normalizeRelationIds } from '~/shared/apiRelations' +import { extractCollection } from '~/shared/utils/apiHelpers' export interface Document { id: string @@ -34,23 +35,6 @@ export interface DocumentResult { const documents = ref([]) const loading = ref(false) -const extractCollection = (payload: unknown): Document[] => { - if (Array.isArray(payload)) { - return payload - } - const p = payload as Record | null - if (Array.isArray(p?.member)) { - return p.member as Document[] - } - if (Array.isArray(p?.['hydra:member'])) { - return p['hydra:member'] as Document[] - } - if (Array.isArray(p?.data)) { - return p.data as Document[] - } - return [] -} - const fileToBase64 = (file: File): Promise => new Promise((resolve, reject) => { const reader = new FileReader() diff --git a/app/composables/usePieces.ts b/app/composables/usePieces.ts index 0ccab82..cd11e81 100644 --- a/app/composables/usePieces.ts +++ b/app/composables/usePieces.ts @@ -4,6 +4,7 @@ import { useApi } from './useApi' import { buildConstructeurRequestPayload, uniqueConstructeurIds } from '~/shared/constructeurUtils' import { useConstructeurs, type Constructeur } from './useConstructeurs' import { extractRelationId, normalizeRelationIds } from '~/shared/apiRelations' +import { extractCollection } from '~/shared/utils/apiHelpers' export interface Piece { id: string @@ -46,23 +47,6 @@ const pieces = ref([]) const total = ref(0) const loading = ref(false) -const extractCollection = (payload: unknown): Piece[] => { - if (Array.isArray(payload)) { - return payload as Piece[] - } - const p = payload as Record | null - if (Array.isArray(p?.member)) { - return p.member as Piece[] - } - if (Array.isArray(p?.['hydra:member'])) { - return p['hydra:member'] as Piece[] - } - if (Array.isArray(p?.data)) { - return p.data as Piece[] - } - return [] -} - const extractTotal = (payload: unknown, fallbackLength: number): number => { const p = payload as Record | null if (typeof p?.totalItems === 'number') { diff --git a/app/composables/useProducts.ts b/app/composables/useProducts.ts index 065e501..07167a0 100644 --- a/app/composables/useProducts.ts +++ b/app/composables/useProducts.ts @@ -4,6 +4,7 @@ import { useApi } from './useApi' import { buildConstructeurRequestPayload, uniqueConstructeurIds } from '~/shared/constructeurUtils' import { useConstructeurs, type Constructeur } from './useConstructeurs' import { extractRelationId, normalizeRelationIds } from '~/shared/apiRelations' +import { extractCollection } from '~/shared/utils/apiHelpers' export interface Product { id: string @@ -62,23 +63,6 @@ const replaceInCache = (item: Product): boolean => { return false } -const extractCollection = (payload: unknown): Product[] => { - if (Array.isArray(payload)) { - return payload as Product[] - } - const p = payload as Record | null - if (Array.isArray(p?.member)) { - return p.member as Product[] - } - if (Array.isArray(p?.['hydra:member'])) { - return p['hydra:member'] as Product[] - } - if (Array.isArray(p?.data)) { - return p.data as Product[] - } - return [] -} - const extractTotal = (payload: unknown, fallbackLength: number): number => { const p = payload as Record | null if (typeof p?.totalItems === 'number') { diff --git a/app/composables/useSites.ts b/app/composables/useSites.ts index 022ba56..b6e23bd 100644 --- a/app/composables/useSites.ts +++ b/app/composables/useSites.ts @@ -1,6 +1,7 @@ import { ref } from 'vue' import { useToast } from './useToast' import { useApi } from './useApi' +import { extractCollection } from '~/shared/utils/apiHelpers' export interface Site { id: string @@ -24,23 +25,6 @@ interface SiteResult { const sites = ref([]) const loading = ref(false) -const extractCollection = (payload: unknown): Site[] => { - if (Array.isArray(payload)) { - return payload as Site[] - } - const p = payload as Record | null - if (Array.isArray(p?.member)) { - return p.member as Site[] - } - if (Array.isArray(p?.['hydra:member'])) { - return p['hydra:member'] as Site[] - } - if (Array.isArray(p?.data)) { - return p.data as Site[] - } - return [] -} - export function useSites() { const { showSuccess, showInfo } = useToast() const { get, post, patch, delete: del } = useApi() @@ -49,8 +33,6 @@ export function useSites() { loading.value = true try { const result = await get('/sites') - console.log('sites api result', result) - if (result.success) { const collection = extractCollection(result.data) sites.value = collection diff --git a/app/shared/utils/apiHelpers.ts b/app/shared/utils/apiHelpers.ts new file mode 100644 index 0000000..54e9640 --- /dev/null +++ b/app/shared/utils/apiHelpers.ts @@ -0,0 +1,16 @@ +/** + * Shared API response helpers. + * + * Extracted from 10+ composables/components that each had an identical local + * copy of extractCollection (parsing hydra:member / member / data / array). + */ + +export function extractCollection(payload: unknown): T[] { + if (Array.isArray(payload)) return payload as T[] + const p = payload as Record | null + if (Array.isArray(p?.member)) return p!.member as T[] + if (Array.isArray(p?.['hydra:member'])) return p!['hydra:member'] as T[] + if (Array.isArray(p?.items)) return p!.items as T[] + if (Array.isArray(p?.data)) return p!.data as T[] + return [] +}