useEntityFetch.ts 1.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758
  1. import type { AsyncData } from '#app'
  2. import type { ComputedRef, Ref } from 'vue'
  3. import { v4 as uuid4 } from 'uuid'
  4. import { useEntityManager } from '~/composables/data/useEntityManager'
  5. import ApiResource from '~/models/ApiResource'
  6. import type { AssociativeArray, Collection } from '~/types/data'
  7. interface useEntityFetchReturnType {
  8. fetch: (
  9. model: typeof ApiResource,
  10. id: number,
  11. ) => AsyncData<ApiResource | null, Error | null>
  12. fetchCollection: (
  13. model: typeof ApiResource,
  14. parent?: ApiResource | null,
  15. query?: Ref<AssociativeArray>,
  16. ) => AsyncData<Collection | null, Error | null>
  17. getRef: <T extends ApiResource>(
  18. model: new () => T,
  19. id: Ref<number | null>,
  20. ) => ComputedRef<null | T>
  21. }
  22. // TODO: améliorer le typage des fonctions sur le modèle de getRef
  23. export const useEntityFetch = (
  24. lazy: boolean = false,
  25. ): useEntityFetchReturnType => {
  26. const { em } = useEntityManager()
  27. const fetch = (model: typeof ApiResource, id: number) =>
  28. useAsyncData(
  29. model.entity + '_' + id + '_' + uuid4(),
  30. () => em.fetch(model, id, true),
  31. { lazy },
  32. )
  33. const fetchCollection = (
  34. model: typeof ApiResource,
  35. parent: ApiResource | null = null,
  36. query: Ref<AssociativeArray | null> = ref(null),
  37. ) =>
  38. useAsyncData(
  39. model.entity + '_many_' + uuid4(),
  40. () => em.fetchCollection(model, parent, query.value ?? undefined),
  41. { lazy },
  42. )
  43. const getRef = <T extends ApiResource>(
  44. model: new () => T,
  45. id: Ref<number | null>,
  46. ): ComputedRef<T | null> => {
  47. return computed(() => (id.value ? (em.find(model, id.value) as T) : null))
  48. }
  49. return { fetch, fetchCollection, getRef }
  50. }