From 0a1e9536cdb8458075f42bd8709f2fdab6166e8b Mon Sep 17 00:00:00 2001 From: Lucien Cartier-Tilet Date: Mon, 8 May 2023 03:01:17 +0200 Subject: [PATCH] feat: handle API calls and caching through Vue components BREAKING CHANGE: API calls and cache no longer made in their respective composable --- content/.vuepress/client.ts | 12 ++-- content/.vuepress/components/ApiLoader.vue | 53 ++++++++++++++++ content/.vuepress/components/Cache.vue | 60 +++++++++++++++++++ .../{ => GitRepos}/GithubRepository.vue | 4 +- .../components/GitRepos/ListRepositories.vue | 50 ++++++++++++++++ .../components/LatestRepositories.vue | 44 -------------- content/.vuepress/composables/cache.ts | 46 -------------- content/.vuepress/composables/github.ts | 39 +----------- content/projects.md | 2 +- 9 files changed, 176 insertions(+), 134 deletions(-) create mode 100644 content/.vuepress/components/ApiLoader.vue create mode 100644 content/.vuepress/components/Cache.vue rename content/.vuepress/components/{ => GitRepos}/GithubRepository.vue (87%) create mode 100644 content/.vuepress/components/GitRepos/ListRepositories.vue delete mode 100644 content/.vuepress/components/LatestRepositories.vue delete mode 100644 content/.vuepress/composables/cache.ts diff --git a/content/.vuepress/client.ts b/content/.vuepress/client.ts index 7db4631..75274c4 100644 --- a/content/.vuepress/client.ts +++ b/content/.vuepress/client.ts @@ -1,15 +1,17 @@ import { defineClientConfig } from '@vuepress/client'; -import PreviewImage from './components/PreviewImage.vue'; import ResponsiveImage from './components/ResponsiveImage.vue'; -import LatestRepositories from './components/LatestRepositories.vue'; -import GithubRepository from './components/GithubRepository.vue'; +import ListRepositories from './components/GitRepos/ListRepositories.vue'; +import GithubRepository from './components/GitRepos/GithubRepository.vue'; +import ApiLoader from './components/ApiLoader.vue'; +import Cache from './components/Cache.vue'; export default defineClientConfig({ enhance({ app }) { - app.component('PreviewImage', PreviewImage); app.component('ResponsiveImage', ResponsiveImage); - app.component('LatestRepositories', LatestRepositories); + app.component('ListRepositories', ListRepositories); app.component('GithubRepository', GithubRepository); + app.component('ApiLoader', ApiLoader); + app.component('Cache', Cache); }, setup() {}, layouts: {}, diff --git a/content/.vuepress/components/ApiLoader.vue b/content/.vuepress/components/ApiLoader.vue new file mode 100644 index 0000000..a4f2777 --- /dev/null +++ b/content/.vuepress/components/ApiLoader.vue @@ -0,0 +1,53 @@ + + + + + diff --git a/content/.vuepress/components/Cache.vue b/content/.vuepress/components/Cache.vue new file mode 100644 index 0000000..3e3f414 --- /dev/null +++ b/content/.vuepress/components/Cache.vue @@ -0,0 +1,60 @@ + + + diff --git a/content/.vuepress/components/GithubRepository.vue b/content/.vuepress/components/GitRepos/GithubRepository.vue similarity index 87% rename from content/.vuepress/components/GithubRepository.vue rename to content/.vuepress/components/GitRepos/GithubRepository.vue index c0ef296..fd951ef 100644 --- a/content/.vuepress/components/GithubRepository.vue +++ b/content/.vuepress/components/GitRepos/GithubRepository.vue @@ -12,7 +12,7 @@ + + diff --git a/content/.vuepress/components/LatestRepositories.vue b/content/.vuepress/components/LatestRepositories.vue deleted file mode 100644 index 3f35f88..0000000 --- a/content/.vuepress/components/LatestRepositories.vue +++ /dev/null @@ -1,44 +0,0 @@ - - - - - diff --git a/content/.vuepress/composables/cache.ts b/content/.vuepress/composables/cache.ts deleted file mode 100644 index 2304b6c..0000000 --- a/content/.vuepress/composables/cache.ts +++ /dev/null @@ -1,46 +0,0 @@ -import { Observable, of } from 'rxjs'; - -const cacheAgeLimitInMilliseconds = 1000 * 60 * 60; - -export function isDataOutdated(name: string): boolean { - const lastUpdated: number = +localStorage.getItem(name + '-timestamp'); - const now: number = Date.now(); - const elapsedTime: number = now - lastUpdated; - return elapsedTime > cacheAgeLimitInMilliseconds; -} - -export function storeInCache( - data: Observable, - name: string -): Observable { - data.subscribe({ - next: (response: T) => { - localStorage.setItem(name, JSON.stringify(response)); - localStorage.setItem(name + '-timestamp', `${Date.now()}`); - }, - }); - return data; -} - -export function readFromCache( - name: string, - callback: () => Observable -): Observable { - let data: Observable; - if (isDataOutdated(name)) { - data = storeInCache(callback(), name); - } else { - let dataFromCache = localStorage.getItem(name); - try { - data = of(JSON.parse(dataFromCache)); - } catch (err) { - console.error( - `Could not parse ${JSON.stringify( - dataFromCache - )}: ${err}. Fetching again data from callback function.` - ); - data = storeInCache(callback(), name); - } - } - return data; -} diff --git a/content/.vuepress/composables/github.ts b/content/.vuepress/composables/github.ts index d531fb9..0b98094 100644 --- a/content/.vuepress/composables/github.ts +++ b/content/.vuepress/composables/github.ts @@ -1,6 +1,3 @@ -import { Observable, switchMap, map } from 'rxjs'; -import { fromFetch } from 'rxjs/fetch'; - export interface GithubRepo { id: number; node_id: string; @@ -48,9 +45,9 @@ export interface GithubRepo { labels_url: string; releases_url: string; deployments_url: string; - created_at: Date; - updated_at: Date; - pushed_at: Date; + created_at: string; + updated_at: string; + pushed_at: string; git_url: string; ssh_url: string; clone_url: string; @@ -107,33 +104,3 @@ export interface GithubError { message: string; documentation_url: string; } - -export function getLatestRepositories( - user: string, - amount: number -): Observable { - return getRepositoriesOfUser(user).pipe( - map((repositories: GithubRepo[]) => { - return repositories - .sort( - (a: GithubRepo, b: GithubRepo) => - +b.updated_at - +a.updated_at - ) - .slice(0, amount); - }) - ); -} - -export function getRepositoriesOfUser(user: string): Observable { - const fetchUrl = `https://api.github.com/users/${user}/repos`; - return fromFetch(fetchUrl).pipe( - switchMap((response: Response) => { - if (response.ok) { - return response.json(); - } else { - console.error(`Error ${response.status}: ${JSON.stringify(response)}`); - return []; - } - }), - ); -} diff --git a/content/projects.md b/content/projects.md index f63cde5..96f0810 100644 --- a/content/projects.md +++ b/content/projects.md @@ -4,7 +4,7 @@ title: Projets # Programmation ## Projets GitHub les plus étoilés - + ## Derniers dépôts de code actifs sur GitHub