From 1c836dc303bc7f3c4391855586eb3e6fbc6ca6e4 Mon Sep 17 00:00:00 2001 From: Aaron van den Berg Date: Wed, 19 Jun 2024 16:56:20 +0200 Subject: [PATCH] Main: Add support for console API pagination on /list endpoints --- src/hooks/useDynamicConfigs.ts | 50 ++++++++++++++++++++++++---------- src/hooks/useExperiments.ts | 46 +++++++++++++++++++++++-------- 2 files changed, 70 insertions(+), 26 deletions(-) diff --git a/src/hooks/useDynamicConfigs.ts b/src/hooks/useDynamicConfigs.ts index a09459e..35f6082 100644 --- a/src/hooks/useDynamicConfigs.ts +++ b/src/hooks/useDynamicConfigs.ts @@ -2,28 +2,50 @@ import type {DynamicConfig} from "~types/statsig"; import {useLocalStorage} from "@uidotdev/usehooks"; import {api} from "~helpers/fetcher"; +import {useEffect, useState} from "react"; import useSWR from "swr"; +const limit = 100; + export const useDynamicConfigs = (): { - error: null | string, - dynamicConfigs: DynamicConfig[], - isLoading: boolean, + dynamicConfigs: DynamicConfig[], + error: null | string, + isLoading: boolean, } => { - const [apiKey] = useLocalStorage("statsig-console-api-key"); - const {data, isLoading} = useSWR(apiKey ? '/dynamic_configs' : null, () => api.get('/dynamic_configs', { - headers: { - "STATSIG-API-KEY": apiKey as string, + const [page, setPage] = useState(1); + const [dynamicConfigs, setDynamicConfigs] = useState([]); + const [apiKey] = useLocalStorage("statsig-console-api-key"); + + const { data, error, isLoading } = useSWR(apiKey ? ['/dynamic_configs', page] : null, () => + api.get('/dynamic_configs', { + headers: { + "STATSIG-API-KEY": apiKey as string, + }, + params: { + limit, + page, + } + }).then(res => res.data) + .catch(err => err) + ); + + useEffect(() => { + if (data?.data && data?.pagination?.totalItems > dynamicConfigs.length) { + setDynamicConfigs(prev => [...prev, ...data.data]); + } + }, [data]); + + useEffect(() => { + if (data?.pagination?.totalItems && dynamicConfigs.length < data.pagination.totalItems) { + setPage(prev => prev + 1); } - }).then(res => res.data) - .catch(err => err) - ); + }, [dynamicConfigs]); - const error = data?.status || !data?.data ? 'An error occurred while fetching dynamic configs data.' : null; - const dynamicConfigs = data?.data || []; + const fetchError = error ? 'An error occurred while fetching experiment data.' : null; return { - error, dynamicConfigs, + error: fetchError, isLoading, - }; + }; }; diff --git a/src/hooks/useExperiments.ts b/src/hooks/useExperiments.ts index 8336b15..f66a2fa 100644 --- a/src/hooks/useExperiments.ts +++ b/src/hooks/useExperiments.ts @@ -1,28 +1,50 @@ -import type {Experiment} from "~types/statsig"; +import type { Experiment } from "~types/statsig"; -import {useLocalStorage} from "@uidotdev/usehooks"; -import {api} from "~helpers/fetcher"; +import { useLocalStorage } from "@uidotdev/usehooks"; +import { api } from "~helpers/fetcher"; +import { useEffect, useState } from "react"; import useSWR from "swr"; +const limit = 100; + export const useExperiments = (): { error: null | string, experiments: Experiment[], isLoading: boolean, } => { + const [page, setPage] = useState(1); + const [experiments, setExperiments] = useState([]); const [apiKey] = useLocalStorage("statsig-console-api-key"); - const {data, isLoading} = useSWR(apiKey ? '/experiments' : null, () => api.get('/experiments', { - headers: { - "STATSIG-API-KEY": apiKey as string, - } - }).then(res => res.data) - .catch(err => err) + + const { data, error, isLoading } = useSWR(apiKey ? ['/experiments', page] : null, ([url, page]) => + api.get(url, { + headers: { + "STATSIG-API-KEY": apiKey as string, + }, + params: { + limit, + page, + } + }).then(res => res.data) + .catch(err => err) ); - const error = data?.status || !data?.data ? 'An error occurred while fetching experiment data.' : null; - const experiments = data?.data || []; + useEffect(() => { + if (data?.data && data?.pagination?.totalItems > experiments.length) { + setExperiments(prev => [...prev, ...data.data]); + } + }, [data]); + + useEffect(() => { + if (data?.pagination?.totalItems && experiments.length < data.pagination.totalItems) { + setPage(prev => prev + 1); + } + }, [experiments]); + + const fetchError = error ? 'An error occurred while fetching experiment data.' : null; return { - error, + error: fetchError, experiments, isLoading, };