<template>
<div v-if="loading"><loading></loading></div>
<div v-else-if="error"><error v-bind="error"/></div>
<div v-else>
<div class="title" v-if="!error"> <h1>Recently Added:</h1></div>
<section class="adverts" >
<adverts @update:isFavorited="updateIsFavorited" v-for="advert in adverts.list" v-bind:key="advert.id" v-bind="advert" />
</section>
</div>
</template>
<script lang="ts">
import { defineComponent, reactive, watchEffect } from 'vue';
import { useQuery } from '@vue/apollo-composable'
import { GET_ADVERTS } from "@/graphql/advert";
import Adverts from '../components/Adverts.vue';
import Error from '../components/Error.vue';
import Loading from '../components/Error.vue';
interface Advert {
id: number;
location: string;
price: number;
title: string;
createdAt: string;
available: boolean;
isFavorited: boolean;
}
export default defineComponent({
name: 'App',
components: {
Adverts,
Error,
Loading,
},
methods: {
async loadMoreAdverts() {
if (this.loading) return;
const accessToken = localStorage.getItem("access_token") || "";
this.loading = true;
try {
const { result, error } = await useQuery(GET_ADVERTS, {
variables: {
accessToken,
offset: this.adverts.list.length,
limit: 10
}
});
if (result) {
this.adverts.list.push(...result.value.getAdverts);
} else if (error) {
console.error(error);
}
} catch (error) {
console.error(error);
} finally {
this.loading = false;
}
}
},
setup() {
const adverts = reactive({ list: [] as Advert[] });
const accessToken = localStorage.getItem("access_token") || "";
const updateIsFavorited = (id: number, isFavorited: boolean) => {
const index = adverts.list.findIndex((advert) => advert.id === id);
const updatedAdverts = [...adverts.list];
updatedAdverts[index] = { ...updatedAdverts[index], isFavorited };
adverts.list = updatedAdverts;
};
const {result, loading, error} = useQuery(GET_ADVERTS, { accessToken, offset: 1, limit: 4 }, { fetchPolicy: 'network-only' });
console.log(result, loading, error);
watchEffect(() => {
if (result.value) {
adverts.list = result.value.getAdverts;
}
});
return {
adverts,
loading,
error,
updateIsFavorited
};
},
mounted() {
// this.loadMoreAdverts();
// const observer = new IntersectionObserver(entries => {
// if (entries[0].isIntersecting) {
// this.loadMoreAdverts();
// }
// }, { threshold: 1 });
// observer.observe(this.$refs.loadMoreTrigger);
},
});
</script>
<style scoped>
.adverts {
display:flex;
justify-content:flex-start;
align-items:center;
flex-direction: row;
flex-wrap:wrap;
gap:30px 30px;
margin:50px 150px;
}
.error {
height:100%;
}
.title {
display:grid;
}
h1 {
color: rgb(var(--v-theme-text));
margin: 50px 150px 20px 150px;
justify-self: flex-start;
}
</style>
i have this code, it fetch adverts, but every time on load i see error message for 1 sec or less,
this pattern is from official documentation https://apollo.vuejs.org/guide-composable/query.html, and i dont think it should work like that, i think it should display loading but not error, because when i check error.value in script it is null