들어가기
예를 들어, 손흥민 팔로우를 loading한다고 할때, data가 너무 많으면,
loading시 error가 날수도 있고, server가 힘들진다.
따라서, 스크롤이 화면 아래에 왔을때, 이어서 3~4개의 data를 loading하게
하는것, 여기서 feed부분만 설정해 본다
import { gql } from 'apollo-server'
export default gql`
type Query {
seeFeed(offset: Int!): [Photo]
}
`
variables에 offset을 변수로 받도록 설정한다.
import prisma from '../../client'
import { protectedResolver } from '../../users/users.util'
export default {
Query: {
seeFeed: protectedResolver((_, { offset }, { loggedInUser }) =>
///1.offset을 variables로 받도록 설정함
prisma.photo.findMany({
take: 2,
skip: offset,
///take: 2는 맨 처음에 2개의 data를 불러온다는 뜻.
///skip: offset 은 이후는 offset의 값에 따라 data를 불러 오겠다는 의미
///나머지 부분은 front 에서 설정함.
where: {
OR: [
{
user: {
followers: { some: { id: loggedInUser.id } },
},
},
{ userId: loggedInUser.id },
],
},
orderBy: { createdAt: 'desc' },
})
),
},
}
import React, { useEffect, useState } from 'react'
import { FlatList } from 'react-native'
import styled from 'styled-components/native'
import { gql, useQuery } from '@apollo/client'
import useUser from '../useUser'
import ScreenLayout from '../components/ScreenLayout'
import Photo from '../components/Photo'
const Button = styled.TouchableOpacity`
background-color: tomato;
padding: 13px 10px;
border-radius: 3px;
width: 100%;
opacity: ${(props) => (props.disabled ? '0.5' : '1')};
`
export const FEED_QUERY = gql`
query seeFeed($offset: Int!) {
seeFeed(offset: $offset) {
///1. offset 값을 variables로 받도록 설정해 줌.
id
user {
username
avatar
}
file
caption
likes
commentNumber
createdAt
isMine
isLiked
comments {
id
user {
username
avatar
}
payload
isMine
createdAt
}
}
}
`
export default function Feed() {
const User = useUser()
console.log(User)
const { data, loading, refetch, fetchMore } = useQuery(FEED_QUERY, {
///2. fetchMore를 useQuery에서 불러와줌.
variables: {
offset: 0,
///3. offset의 default 값은 0으로 설정해줌.
},
})
const renderPhoto = ({ item: photo }) => {
return <Photo {...photo} />
}
const refresh = async () => {
setRefreshing(true)
await refetch()
setRefreshing(false)
}
const [refreshing, setRefreshing] = useState(false)
return (
<ScreenLayout loading={loading}>
<FlatList
onEndReachedThreshold={0.05}
onEndReached={() =>
fetchMore({
variables: {
offset: data?.seeFeed?.length,
},
})
}
/// 4. onEndReachedThreshold는 화면 어느부분에 갔을데 fetchMore할지 설정
/// 값이 0이면 화면 맨 아래에 도달했을때, fetchMore가 이루어짐.
/// 5. onEndReached는 함수를 받는데, onEndReachedThreshold에서 설정한
/// 화면의 값에 도달하면 실행될 함수를 압력함.
/// fetchMore를 실행시키고, variables의 offset은 맨처음 불려진 data 실이만큼
/// 디시 loading한다는 의미, 2,3,4 아무거나 입력해도 상관 없음.
refreshing={refreshing}
onRefresh={refresh}
style={{ width: '100%' }}
showsVerticalScrollIndicator={false}
data={data?.seeFeed}
keyExtractor={(photo) => '' + photo.id}
renderItem={renderPhoto}
/>
</ScreenLayout>
)
}
import {
makeVar,
ApolloClient,
InMemoryCache,
createHttpLink,
} from '@apollo/client'
import { setContext } from '@apollo/client/link/context'
import { offsetLimitPagination } from '@apollo/client/utilities'
import AsyncStorage from '@react-native-async-storage/async-storage'
export const isLoggedInVar = makeVar(false)
export const tokenVar = makeVar('')
export const TOKEN = 'token'
export const logUserIn = async (token) => {
await AsyncStorage.setItem(TOKEN, token)
isLoggedInVar(true)
tokenVar(token)
}
export const logUserOut = async () => {
await AsyncStorage.removeItem(TOKEN)
isLoggedInVar(false)
tokenVar(null)
}
const httpLink = createHttpLink({
uri: 'http://10.0.2.2:4000/graphql',
})
const authLink = setContext((_, { headers }) => {
return {
headers: {
...headers,
token: tokenVar(),
},
}
})
export const cache = new InMemoryCache({
typePolicies: {
Query: {
fields: {
seeFeed: offsetLimitPagination(),
},
},
},
})
/// 마지막으로 InMemoryCache에 typePolicies:{ Query: {fields: {
/// 에 infiniteScroll이 될 Query를 넣어준다음, offsetLimitPagination()을 넣어줌.
export const client = new ApolloClient({
link: authLink.concat(httpLink),
cache,
})
https://motionmod.net/ is a powerful mobile app for editing videos and animations. It includes features like multiple layers, blending modes, and keyframe animation, allowing users to create high-quality content.
https://fluxus.mobi/ is a top choice for Roblox Executors due to its compatibility with both mobile and PC platforms. Meanwhile, https://solaraexecutor.com/ is a new Windows executor with 52% UNC support and is a level 3 executor. However, it cannot currently bypass Byfron/Hyperion, so using alt accounts for Roblox exploits is recommended.