From d101d4121a3b62b02ff7df617f49e828659c777e Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Wed, 25 Sep 2024 10:14:16 +0530 Subject: [PATCH 01/15] added function to initially load 20 users and then load more users as we scroll, changed data fetching structure to fetch last user id --- users/discord/App.js | 29 +++++++++++++ users/discord/components/UsersSection.js | 53 +++++++++++++++--------- users/discord/style.css | 3 +- users/discord/utils/util.js | 9 +++- 4 files changed, 72 insertions(+), 22 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 87fa873d..404a5a54 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -19,8 +19,34 @@ const urlParams = new URLSearchParams(window.location.search); let activeTab = urlParams.get('tab') ?? 'in_discord'; let showUser = 0; +let isLoading = false; +const USERS_PER_FETCH = 20; + usersData[activeTab] = await getUsers(activeTab); +const fetchMoreUsers = async () => { + if (isLoading || !usersData[activeTab]) { + return; + } + isLoading = true; + const lastUserId = usersData[activeTab][usersData[activeTab].length - 1]?.id; + try { + const newUsers = await getUsers(activeTab, lastUserId, USERS_PER_FETCH); + usersData[activeTab] = [...usersData[activeTab], ...newUsers]; + isLoading = false; + rerender(App(), window['root']); + } catch (error) { + console.error('Error fetching users', error); + isLoading = false; + } +}; +const handleScroll = (e) => { + const { scrollTop, clientHeight, scrollHeight } = e.target; + if (scrollHeight - scrollTop <= clientHeight + 100) { + fetchMoreUsers(); + } +}; + const handleTabNavigation = async (e) => { const selectedTabId = e.target.getAttribute('data_key'); if (selectedTabId) { @@ -60,6 +86,8 @@ export const App = () => { users, showUser, handleUserSelected, + handleScroll, + isLoading, }), UserDetailsSection({ user: users[showUser] ?? {} }), ]); @@ -69,3 +97,4 @@ export const App = () => { NoUserFound(), ]); }; +fetchMoreUsers(); diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index bc07cdaa..b55cd28e 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -1,26 +1,39 @@ const { createElement } = react; -export const UsersSection = ({ users, showUser, handleUserSelected }) => { +export const UsersSection = ({ + users, + showUser, + handleUserSelected, + handleScroll, + isLoading, +}) => { return createElement( 'aside', - { class: 'users_section', onclick: handleUserSelected }, - users?.map((user) => { - return createElement( - 'div', - { - class: `user_card ${ - users[showUser].id === user.id ? 'active_tab' : '' - }`, - data_key: user.id, - }, - [ - createElement('img', { - src: user?.picture?.url ?? dummyPicture, - class: 'user_image', - }), - createElement('span', {}, [user.first_name + ' ' + user.last_name]), - ], - ); - }), + { + class: 'users_section', + onclick: handleUserSelected, + onscroll: handleScroll, + }, + [ + ...users?.map((user) => { + return createElement( + 'div', + { + class: `user_card ${ + users[showUser].id === user.id ? 'active_tab' : '' + }`, + data_key: user.id, + }, + [ + createElement('img', { + src: user?.picture?.url ?? dummyPicture, + class: 'user_image', + }), + createElement('span', {}, [user.first_name + ' ' + user.last_name]), + ], + ); + }), + isLoading && createElement('div', 'Load more users...'), + ], ); }; diff --git a/users/discord/style.css b/users/discord/style.css index 23058547..f71d7a51 100644 --- a/users/discord/style.css +++ b/users/discord/style.css @@ -19,8 +19,9 @@ main { .users_section { grid-area: aside; - overflow: scroll; + overflow: auto; padding-inline: 1rem; + max-height: 80vh; } .tabs_section { diff --git a/users/discord/utils/util.js b/users/discord/utils/util.js index 83cd40e5..649162f5 100644 --- a/users/discord/utils/util.js +++ b/users/discord/utils/util.js @@ -1,8 +1,12 @@ -export const getUsers = async (tab) => { +export const getUsers = async (tab, lastUserId = null, limit = 20) => { let URL = { in_discord: `${API_BASE_URL}/users/search/?role=in_discord`, verified: `${API_BASE_URL}/users/search/?verified=true`, }; + if (lastUserId) { + URL[tab] += `&last_id=${lastUserId}`; + } + URL[tab] += `&limit=${limit}`; try { const response = await fetch(URL[tab], { @@ -12,6 +16,9 @@ export const getUsers = async (tab) => { 'Content-type': 'application/json', }, }); + if (!response.ok) { + console.error('Failed to fetch:', response.status, response.statusText); + } const data = await response.json(); return data.users ?? []; From efd2e8806611e0ab20e83b3b4f7afdaaaad6794a Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Tue, 8 Oct 2024 21:30:38 +0530 Subject: [PATCH 02/15] fetching mock users and handling fetch more users --- users/discord/App.js | 562 +++++++++++++++++++++-- users/discord/components/UsersSection.js | 58 ++- users/discord/utils/util.js | 9 +- 3 files changed, 572 insertions(+), 57 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 404a5a54..22a928fc 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -5,6 +5,518 @@ import { getUsers } from './utils/util.js'; import { NoUserFound } from './components/NoUserFound.js'; const { createElement, rerender } = react; +const mockUsersData = { + in_discord: [ + { + id: 'user_1', + discordId: '123456789', + username: 'Alice', + avatar: 'https://placekitten.com/50/50?image=1', + }, + { + id: 'user_2', + username: 'Bob', + avatar: 'https://placekitten.com/50/50?image=2', + }, + { + id: 'user_3', + username: 'Charlie', + avatar: 'https://placekitten.com/50/50?image=3', + }, + { + id: 'user_4', + username: 'David', + avatar: 'https://placekitten.com/50/50?image=4', + }, + { + id: 'user_5', + username: 'Eve', + avatar: 'https://placekitten.com/50/50?image=5', + }, + { + id: 'user_6', + username: 'Fay', + avatar: 'https://placekitten.com/50/50?image=6', + }, + { + id: 'user_7', + username: 'George', + avatar: 'https://placekitten.com/50/50?image=7', + }, + { + id: 'user_8', + username: 'Hannah', + avatar: 'https://placekitten.com/50/50?image=8', + }, + { + id: 'user_9', + username: 'Isaac', + avatar: 'https://placekitten.com/50/50?image=9', + }, + { + id: 'user_10', + username: 'Jill', + avatar: 'https://placekitten.com/50/50?image=10', + }, + { + id: 'user_11', + username: 'Karl', + avatar: 'https://placekitten.com/50/50?image=11', + }, + { + id: 'user_12', + username: 'Lily', + avatar: 'https://placekitten.com/50/50?image=12', + }, + { + id: 'user_13', + username: 'Max', + avatar: 'https://placekitten.com/50/50?image=13', + }, + { + id: 'user_14', + username: 'Nina', + avatar: 'https://placekitten.com/50/50?image=14', + }, + { + id: 'user_15', + username: 'Oscar', + avatar: 'https://placekitten.com/50/50?image=15', + }, + { + id: 'user_16', + username: 'Pam', + avatar: 'https://placekitten.com/50/50?image=16', + }, + { + id: 'user_17', + username: 'Quinn', + avatar: 'https://placekitten.com/50/50?image=17', + }, + { + id: 'user_18', + username: 'Rachel', + avatar: 'https://placekitten.com/50/50?image=18', + }, + { + id: 'user_19', + username: 'Sam', + avatar: 'https://placekitten.com/50/50?image=19', + }, + { + id: 'user_20', + username: 'Tina', + avatar: 'https://placekitten.com/50/50?image=20', + }, + { + id: 'user_21', + username: 'Uma', + avatar: 'https://placekitten.com/50/50?image=21', + }, + { + id: 'user_22', + username: 'Victor', + avatar: 'https://placekitten.com/50/50?image=22', + }, + { + id: 'user_23', + username: 'Wendy', + avatar: 'https://placekitten.com/50/50?image=23', + }, + { + id: 'user_24', + username: 'Xander', + avatar: 'https://placekitten.com/50/50?image=24', + }, + { + id: 'user_25', + username: 'Yvonne', + avatar: 'https://placekitten.com/50/50?image=25', + }, + { + id: 'user_26', + username: 'Zack', + avatar: 'https://placekitten.com/50/50?image=26', + }, + { + id: 'user_27', + username: 'Aaron', + avatar: 'https://placekitten.com/50/50?image=27', + }, + { + id: 'user_28', + username: 'Bianca', + avatar: 'https://placekitten.com/50/50?image=28', + }, + { + id: 'user_29', + username: 'Carlos', + avatar: 'https://placekitten.com/50/50?image=29', + }, + { + id: 'user_30', + username: 'Diana', + avatar: 'https://placekitten.com/50/50?image=30', + }, + { + id: 'user_31', + username: 'Eli', + avatar: 'https://placekitten.com/50/50?image=31', + }, + { + id: 'user_32', + username: 'Fiona', + avatar: 'https://placekitten.com/50/50?image=32', + }, + { + id: 'user_33', + username: 'Gus', + avatar: 'https://placekitten.com/50/50?image=33', + }, + { + id: 'user_34', + username: 'Holly', + avatar: 'https://placekitten.com/50/50?image=34', + }, + { + id: 'user_35', + username: 'Ian', + avatar: 'https://placekitten.com/50/50?image=35', + }, + { + id: 'user_36', + username: 'Julia', + avatar: 'https://placekitten.com/50/50?image=36', + }, + { + id: 'user_37', + username: 'Kevin', + avatar: 'https://placekitten.com/50/50?image=37', + }, + { + id: 'user_38', + username: 'Laura', + avatar: 'https://placekitten.com/50/50?image=38', + }, + { + id: 'user_39', + username: 'Mike', + avatar: 'https://placekitten.com/50/50?image=39', + }, + { + id: 'user_40', + username: 'Nora', + avatar: 'https://placekitten.com/50/50?image=40', + }, + { + id: 'user_41', + username: 'Oliver', + avatar: 'https://placekitten.com/50/50?image=41', + }, + { + id: 'user_42', + username: 'Paula', + avatar: 'https://placekitten.com/50/50?image=42', + }, + { + id: 'user_43', + username: 'Quincy', + avatar: 'https://placekitten.com/50/50?image=43', + }, + { + id: 'user_44', + username: 'Rose', + avatar: 'https://placekitten.com/50/50?image=44', + }, + { + id: 'user_45', + username: 'Steve', + avatar: 'https://placekitten.com/50/50?image=45', + }, + { + id: 'user_46', + username: 'Tara', + avatar: 'https://placekitten.com/50/50?image=46', + }, + { + id: 'user_47', + username: 'Ulysses', + avatar: 'https://placekitten.com/50/50?image=47', + }, + { + id: 'user_48', + username: 'Violet', + avatar: 'https://placekitten.com/50/50?image=48', + }, + { + id: 'user_49', + username: 'Wes', + avatar: 'https://placekitten.com/50/50?image=49', + }, + { + id: 'user_50', + username: 'Xena', + avatar: 'https://placekitten.com/50/50?image=50', + }, + ], + verified: [ + { + id: 'user_51', + username: 'Frank', + avatar: 'https://placekitten.com/50/50?image=51', + }, + { + id: 'user_52', + username: 'Grace', + avatar: 'https://placekitten.com/50/50?image=52', + }, + { + id: 'user_53', + username: 'Henry', + avatar: 'https://placekitten.com/50/50?image=53', + }, + { + id: 'user_54', + username: 'Ivy', + avatar: 'https://placekitten.com/50/50?image=54', + }, + { + id: 'user_55', + username: 'Jack', + avatar: 'https://placekitten.com/50/50?image=55', + }, + { + id: 'user_56', + username: 'Kim', + avatar: 'https://placekitten.com/50/50?image=56', + }, + { + id: 'user_57', + username: 'Leo', + avatar: 'https://placekitten.com/50/50?image=57', + }, + { + id: 'user_58', + username: 'Mila', + avatar: 'https://placekitten.com/50/50?image=58', + }, + { + id: 'user_59', + username: 'Nate', + avatar: 'https://placekitten.com/50/50?image=59', + }, + { + id: 'user_60', + username: 'Olivia', + avatar: 'https://placekitten.com/50/50?image=60', + }, + { + id: 'user_61', + username: 'Paul', + avatar: 'https://placekitten.com/50/50?image=61', + }, + { + id: 'user_62', + username: 'Quinn', + avatar: 'https://placekitten.com/50/50?image=62', + }, + { + id: 'user_63', + username: 'Ruby', + avatar: 'https://placekitten.com/50/50?image=63', + }, + { + id: 'user_64', + username: 'Steve', + avatar: 'https://placekitten.com/50/50?image=64', + }, + { + id: 'user_65', + username: 'Tina', + avatar: 'https://placekitten.com/50/50?image=65', + }, + { + id: 'user_66', + username: 'Ulysses', + avatar: 'https://placekitten.com/50/50?image=66', + }, + { + id: 'user_67', + username: 'Vera', + avatar: 'https://placekitten.com/50/50?image=67', + }, + { + id: 'user_68', + username: 'Walter', + avatar: 'https://placekitten.com/50/50?image=68', + }, + { + id: 'user_69', + username: 'Xena', + avatar: 'https://placekitten.com/50/50?image=69', + }, + { + id: 'user_70', + username: 'Yvonne', + avatar: 'https://placekitten.com/50/50?image=70', + }, + { + id: 'user_71', + username: 'Zane', + avatar: 'https://placekitten.com/50/50?image=71', + }, + { + id: 'user_72', + username: 'Alan', + avatar: 'https://placekitten.com/50/50?image=72', + }, + { + id: 'user_73', + username: 'Bella', + avatar: 'https://placekitten.com/50/50?image=73', + }, + { + id: 'user_74', + username: 'Chris', + avatar: 'https://placekitten.com/50/50?image=74', + }, + { + id: 'user_75', + username: 'Daisy', + avatar: 'https://placekitten.com/50/50?image=75', + }, + { + id: 'user_76', + username: 'Ethan', + avatar: 'https://placekitten.com/50/50?image=76', + }, + { + id: 'user_77', + username: 'Faye', + avatar: 'https://placekitten.com/50/50?image=77', + }, + { + id: 'user_78', + username: 'Gavin', + avatar: 'https://placekitten.com/50/50?image=78', + }, + { + id: 'user_79', + username: 'Holly', + avatar: 'https://placekitten.com/50/50?image=79', + }, + { + id: 'user_80', + username: 'Isaac', + avatar: 'https://placekitten.com/50/50?image=80', + }, + { + id: 'user_81', + username: 'Julia', + avatar: 'https://placekitten.com/50/50?image=81', + }, + { + id: 'user_82', + username: 'Kevin', + avatar: 'https://placekitten.com/50/50?image=82', + }, + { + id: 'user_83', + username: 'Laura', + avatar: 'https://placekitten.com/50/50?image=83', + }, + { + id: 'user_84', + username: 'Mike', + avatar: 'https://placekitten.com/50/50?image=84', + }, + { + id: 'user_85', + username: 'Nina', + avatar: 'https://placekitten.com/50/50?image=85', + }, + { + id: 'user_86', + username: 'Oscar', + avatar: 'https://placekitten.com/50/50?image=86', + }, + { + id: 'user_87', + username: 'Pam', + avatar: 'https://placekitten.com/50/50?image=87', + }, + { + id: 'user_88', + username: 'Quincy', + avatar: 'https://placekitten.com/50/50?image=88', + }, + { + id: 'user_89', + username: 'Rose', + avatar: 'https://placekitten.com/50/50?image=89', + }, + { + id: 'user_90', + username: 'Sam', + avatar: 'https://placekitten.com/50/50?image=90', + }, + { + id: 'user_91', + username: 'Tara', + avatar: 'https://placekitten.com/50/50?image=91', + }, + { + id: 'user_92', + username: 'Uma', + avatar: 'https://placekitten.com/50/50?image=92', + }, + { + id: 'user_93', + username: 'Victor', + avatar: 'https://placekitten.com/50/50?image=93', + }, + { + id: 'user_94', + username: 'Wendy', + avatar: 'https://placekitten.com/50/50?image=94', + }, + { + id: 'user_95', + username: 'Xander', + avatar: 'https://placekitten.com/50/50?image=95', + }, + { + id: 'user_96', + username: 'Yara', + avatar: 'https://placekitten.com/50/50?image=96', + }, + { + id: 'user_97', + username: 'Zeke', + avatar: 'https://placekitten.com/50/50?image=97', + }, + { + id: 'user_98', + username: 'Ava', + avatar: 'https://placekitten.com/50/50?image=98', + }, + { + id: 'user_99', + username: 'Blake', + avatar: 'https://placekitten.com/50/50?image=99', + }, + { + id: 'user_100', + username: 'Chloe', + avatar: 'https://placekitten.com/50/50?image=100', + }, + ], +}; +/* work on pagination with array index for now, forget about last user id. +You should call the API every time the user reaches the end of the page. +Let's say initially you load 10 users- that's index 0,9 then when the user, +reaches bottom of the page you fetch the data again to get the next 10 users- that's index 10,19 +*/ const tabs = [ { display_name: 'In Discord', id: 'in_discord' }, @@ -17,34 +529,34 @@ export const usersData = { const urlParams = new URLSearchParams(window.location.search); let activeTab = urlParams.get('tab') ?? 'in_discord'; - -let showUser = 0; +const INITIAL_USERS = 10; let isLoading = false; -const USERS_PER_FETCH = 20; +let currentPage = 1; +let showUser = 0; +// get mock users +const getMockUser = (tabId, page = 1) => { + const start = (page - 1) * INITIAL_USERS; + const end = start + INITIAL_USERS; + console.log('fetched initial users'); + // currentPage++; + return mockUsersData[tabId].slice(start, end); +}; + +// usersData[activeTab] = await getUsers(activeTab); + +usersData[activeTab] = await getMockUser(activeTab); -usersData[activeTab] = await getUsers(activeTab); +/* create a function to fetch more users (for eg. we initially have 6 users, +we fetch users everytime the user reaches the end of the page.) */ const fetchMoreUsers = async () => { - if (isLoading || !usersData[activeTab]) { - return; - } isLoading = true; - const lastUserId = usersData[activeTab][usersData[activeTab].length - 1]?.id; - try { - const newUsers = await getUsers(activeTab, lastUserId, USERS_PER_FETCH); - usersData[activeTab] = [...usersData[activeTab], ...newUsers]; - isLoading = false; - rerender(App(), window['root']); - } catch (error) { - console.error('Error fetching users', error); - isLoading = false; - } -}; -const handleScroll = (e) => { - const { scrollTop, clientHeight, scrollHeight } = e.target; - if (scrollHeight - scrollTop <= clientHeight + 100) { - fetchMoreUsers(); - } + currentPage++; + const newUsers = await getMockUser(activeTab, currentPage); + usersData[activeTab] = [...usersData[activeTab], ...newUsers]; + console.log(newUsers, 'fetched new users'); + + isLoading = false; }; const handleTabNavigation = async (e) => { @@ -86,8 +598,7 @@ export const App = () => { users, showUser, handleUserSelected, - handleScroll, - isLoading, + fetchMoreUsers, }), UserDetailsSection({ user: users[showUser] ?? {} }), ]); @@ -97,4 +608,3 @@ export const App = () => { NoUserFound(), ]); }; -fetchMoreUsers(); diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index b55cd28e..70f7d8bd 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -4,9 +4,21 @@ export const UsersSection = ({ users, showUser, handleUserSelected, - handleScroll, - isLoading, + fetchMoreUsers, }) => { + const handleScroll = (e) => { + console.log('scroll triggered'); + + const container = e.target; + const { scrollTop, scrollHeight, clientHeight } = container; + if (scrollTop + clientHeight >= scrollHeight - 5) { + isLoading = true; + console.log('user scrolling'); + fetchMoreUsers(); + } + }; + + // handle scroll is not working - add event listener on every scroll element return createElement( 'aside', { @@ -14,26 +26,26 @@ export const UsersSection = ({ onclick: handleUserSelected, onscroll: handleScroll, }, - [ - ...users?.map((user) => { - return createElement( - 'div', - { - class: `user_card ${ - users[showUser].id === user.id ? 'active_tab' : '' - }`, - data_key: user.id, - }, - [ - createElement('img', { - src: user?.picture?.url ?? dummyPicture, - class: 'user_image', - }), - createElement('span', {}, [user.first_name + ' ' + user.last_name]), - ], - ); - }), - isLoading && createElement('div', 'Load more users...'), - ], + users?.map((user) => { + return createElement( + 'div', + { + class: `user_card ${ + users[showUser].id === user.id ? 'active_tab' : '' + }`, + data_key: user.id, + }, + [ + createElement('img', { + src: user?.picture?.url ?? dummyPicture, + class: 'user_image', + }), + // createElement('span', {}, [ + // user.first_name + ' ' + user.last_name + user.username, + // ]), + createElement('span', {}, [user.username]), + ], + ); + }), ); }; diff --git a/users/discord/utils/util.js b/users/discord/utils/util.js index 649162f5..83cd40e5 100644 --- a/users/discord/utils/util.js +++ b/users/discord/utils/util.js @@ -1,12 +1,8 @@ -export const getUsers = async (tab, lastUserId = null, limit = 20) => { +export const getUsers = async (tab) => { let URL = { in_discord: `${API_BASE_URL}/users/search/?role=in_discord`, verified: `${API_BASE_URL}/users/search/?verified=true`, }; - if (lastUserId) { - URL[tab] += `&last_id=${lastUserId}`; - } - URL[tab] += `&limit=${limit}`; try { const response = await fetch(URL[tab], { @@ -16,9 +12,6 @@ export const getUsers = async (tab, lastUserId = null, limit = 20) => { 'Content-type': 'application/json', }, }); - if (!response.ok) { - console.error('Failed to fetch:', response.status, response.statusText); - } const data = await response.json(); return data.users ?? []; From b8f8a20310b00cdc19299ff997a25947ecc85faa Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Thu, 10 Oct 2024 20:29:04 +0530 Subject: [PATCH 03/15] users are getting fetched with scroll but the next set of users are not visible in screen --- users/discord/App.js | 67 +++++++++++++++--------- users/discord/components/UsersSection.js | 33 +++++++----- 2 files changed, 64 insertions(+), 36 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 22a928fc..438f89b8 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -512,11 +512,6 @@ const mockUsersData = { }, ], }; -/* work on pagination with array index for now, forget about last user id. -You should call the API every time the user reaches the end of the page. -Let's say initially you load 10 users- that's index 0,9 then when the user, -reaches bottom of the page you fetch the data again to get the next 10 users- that's index 10,19 -*/ const tabs = [ { display_name: 'In Discord', id: 'in_discord' }, @@ -533,32 +528,52 @@ const INITIAL_USERS = 10; let isLoading = false; let currentPage = 1; let showUser = 0; -// get mock users -const getMockUser = (tabId, page = 1) => { - const start = (page - 1) * INITIAL_USERS; - const end = start + INITIAL_USERS; - console.log('fetched initial users'); - // currentPage++; - return mockUsersData[tabId].slice(start, end); -}; // usersData[activeTab] = await getUsers(activeTab); -usersData[activeTab] = await getMockUser(activeTab); - -/* create a function to fetch more users (for eg. we initially have 6 users, -we fetch users everytime the user reaches the end of the page.) */ +const fetchUsers = async (tabId, page = 1) => { + if (isLoading) return; -const fetchMoreUsers = async () => { isLoading = true; - currentPage++; - const newUsers = await getMockUser(activeTab, currentPage); - usersData[activeTab] = [...usersData[activeTab], ...newUsers]; - console.log(newUsers, 'fetched new users'); + try { + const start = (page - 1) * INITIAL_USERS; + const end = start + INITIAL_USERS; + + const newUsers = mockUsersData[tabId].slice(start, end); - isLoading = false; + if (newUsers.length > 0) { + if (page === 1) { + usersData[tabId] = newUsers; // Initial load + console.log('Fetched initial users'); + } else { + usersData[tabId] = [...usersData[tabId], ...newUsers]; // Append new users + console.log('Fetched more users'); + console.log(usersData[tabId]); + } + currentPage = page; + rerender(App(), window[root]); // Re-render the app with the new users + } else { + console.log('No more users to fetch'); + } + } catch (error) { + console.error('Error fetching users', error); + } finally { + isLoading = false; + } }; +const handleScroll = () => { + const scrollPosition = window.innerHeight + window.scrollY; + const bottomPosition = document.body.offsetHeight - 100; // Trigger fetch 100px from bottom + + if (scrollPosition >= bottomPosition) { + // Fetch more users when the user is near the bottom + fetchUsers(activeTab, currentPage + 1); + } +}; + +window.addEventListener('scroll', handleScroll); + const handleTabNavigation = async (e) => { const selectedTabId = e.target.getAttribute('data_key'); if (selectedTabId) { @@ -598,7 +613,9 @@ export const App = () => { users, showUser, handleUserSelected, - fetchMoreUsers, + fetchUsers, + activeTab, + currentPage, }), UserDetailsSection({ user: users[showUser] ?? {} }), ]); @@ -608,3 +625,5 @@ export const App = () => { NoUserFound(), ]); }; + +fetchUsers(activeTab, 1); diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index 70f7d8bd..8812d193 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -4,27 +4,36 @@ export const UsersSection = ({ users, showUser, handleUserSelected, - fetchMoreUsers, + fetchUsers, + activeTab, + currentPage, }) => { - const handleScroll = (e) => { - console.log('scroll triggered'); - - const container = e.target; - const { scrollTop, scrollHeight, clientHeight } = container; - if (scrollTop + clientHeight >= scrollHeight - 5) { - isLoading = true; - console.log('user scrolling'); - fetchMoreUsers(); - } + const debounce = (func, delay) => { + let timeoutId; + return function (...args) { + clearTimeout(timeoutId); + timeoutId = setTimeout(() => { + func.apply(this, args); + }, delay); + }; }; + window.addEventListener( + 'scroll', + debounce(() => { + console.log('scroll triggered'); + if (window.innerHeight + window.scrollY >= document.body.offsetHeight) { + fetchUsers(activeTab, currentPage + 1); // Fetch next page + } + }, 200), + ); + // handle scroll is not working - add event listener on every scroll element return createElement( 'aside', { class: 'users_section', onclick: handleUserSelected, - onscroll: handleScroll, }, users?.map((user) => { return createElement( From 4e8b4bf4dc0ef982a3a24bd28ada7308baaf0b63 Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Tue, 15 Oct 2024 07:08:38 +0530 Subject: [PATCH 04/15] user list is getting updated --- users/discord/App.js | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 438f89b8..2f3100a4 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -551,7 +551,7 @@ const fetchUsers = async (tabId, page = 1) => { console.log(usersData[tabId]); } currentPage = page; - rerender(App(), window[root]); // Re-render the app with the new users + rerender(App(), document.getElementById('root')); // Re-render the app with the new users } else { console.log('No more users to fetch'); } @@ -562,17 +562,17 @@ const fetchUsers = async (tabId, page = 1) => { } }; -const handleScroll = () => { - const scrollPosition = window.innerHeight + window.scrollY; - const bottomPosition = document.body.offsetHeight - 100; // Trigger fetch 100px from bottom +// const handleScroll = () => { +// const scrollPosition = window.innerHeight + window.scrollY; +// const bottomPosition = document.body.offsetHeight - 100; // Trigger fetch 100px from bottom - if (scrollPosition >= bottomPosition) { - // Fetch more users when the user is near the bottom - fetchUsers(activeTab, currentPage + 1); - } -}; +// if (scrollPosition >= bottomPosition) { +// // Fetch more users when the user is near the bottom +// fetchUsers(activeTab, currentPage + 1); +// } +// }; -window.addEventListener('scroll', handleScroll); +// window.addEventListener('scroll', handleScroll); const handleTabNavigation = async (e) => { const selectedTabId = e.target.getAttribute('data_key'); From f7883ebed46873f1555ec2ff5f0b6395f266b60e Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Tue, 15 Oct 2024 07:23:44 +0530 Subject: [PATCH 05/15] fixed duplicated fetching --- users/discord/App.js | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/users/discord/App.js b/users/discord/App.js index 2f3100a4..2293ccf4 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -546,7 +546,11 @@ const fetchUsers = async (tabId, page = 1) => { usersData[tabId] = newUsers; // Initial load console.log('Fetched initial users'); } else { - usersData[tabId] = [...usersData[tabId], ...newUsers]; // Append new users + const existingIds = new Set(usersData[tabId].map((user) => user.id)); + const uniqueNewUsers = newUsers.filter( + (user) => !existingIds.has(user.id), + ); + usersData[tabId] = [...usersData[tabId], ...uniqueNewUsers]; console.log('Fetched more users'); console.log(usersData[tabId]); } From e4e28f08e8bbab5edfd9aca4f9ad4f432650ddc6 Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Tue, 15 Oct 2024 19:31:36 +0530 Subject: [PATCH 06/15] moved mock data to utils, addded loading state --- users/discord/App.js | 531 +---------------------- users/discord/components/UsersSection.js | 10 +- users/discord/utils/util.js | 508 ++++++++++++++++++++++ 3 files changed, 524 insertions(+), 525 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 2293ccf4..73aeda96 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -1,517 +1,10 @@ import { TabsSection } from './components/TabsSection.js'; import { UsersSection } from './components/UsersSection.js'; import { UserDetailsSection } from './components/UserDetailsSection.js'; -import { getUsers } from './utils/util.js'; +import { getUsers, mockUsersData } from './utils/util.js'; import { NoUserFound } from './components/NoUserFound.js'; const { createElement, rerender } = react; -const mockUsersData = { - in_discord: [ - { - id: 'user_1', - discordId: '123456789', - username: 'Alice', - avatar: 'https://placekitten.com/50/50?image=1', - }, - { - id: 'user_2', - username: 'Bob', - avatar: 'https://placekitten.com/50/50?image=2', - }, - { - id: 'user_3', - username: 'Charlie', - avatar: 'https://placekitten.com/50/50?image=3', - }, - { - id: 'user_4', - username: 'David', - avatar: 'https://placekitten.com/50/50?image=4', - }, - { - id: 'user_5', - username: 'Eve', - avatar: 'https://placekitten.com/50/50?image=5', - }, - { - id: 'user_6', - username: 'Fay', - avatar: 'https://placekitten.com/50/50?image=6', - }, - { - id: 'user_7', - username: 'George', - avatar: 'https://placekitten.com/50/50?image=7', - }, - { - id: 'user_8', - username: 'Hannah', - avatar: 'https://placekitten.com/50/50?image=8', - }, - { - id: 'user_9', - username: 'Isaac', - avatar: 'https://placekitten.com/50/50?image=9', - }, - { - id: 'user_10', - username: 'Jill', - avatar: 'https://placekitten.com/50/50?image=10', - }, - { - id: 'user_11', - username: 'Karl', - avatar: 'https://placekitten.com/50/50?image=11', - }, - { - id: 'user_12', - username: 'Lily', - avatar: 'https://placekitten.com/50/50?image=12', - }, - { - id: 'user_13', - username: 'Max', - avatar: 'https://placekitten.com/50/50?image=13', - }, - { - id: 'user_14', - username: 'Nina', - avatar: 'https://placekitten.com/50/50?image=14', - }, - { - id: 'user_15', - username: 'Oscar', - avatar: 'https://placekitten.com/50/50?image=15', - }, - { - id: 'user_16', - username: 'Pam', - avatar: 'https://placekitten.com/50/50?image=16', - }, - { - id: 'user_17', - username: 'Quinn', - avatar: 'https://placekitten.com/50/50?image=17', - }, - { - id: 'user_18', - username: 'Rachel', - avatar: 'https://placekitten.com/50/50?image=18', - }, - { - id: 'user_19', - username: 'Sam', - avatar: 'https://placekitten.com/50/50?image=19', - }, - { - id: 'user_20', - username: 'Tina', - avatar: 'https://placekitten.com/50/50?image=20', - }, - { - id: 'user_21', - username: 'Uma', - avatar: 'https://placekitten.com/50/50?image=21', - }, - { - id: 'user_22', - username: 'Victor', - avatar: 'https://placekitten.com/50/50?image=22', - }, - { - id: 'user_23', - username: 'Wendy', - avatar: 'https://placekitten.com/50/50?image=23', - }, - { - id: 'user_24', - username: 'Xander', - avatar: 'https://placekitten.com/50/50?image=24', - }, - { - id: 'user_25', - username: 'Yvonne', - avatar: 'https://placekitten.com/50/50?image=25', - }, - { - id: 'user_26', - username: 'Zack', - avatar: 'https://placekitten.com/50/50?image=26', - }, - { - id: 'user_27', - username: 'Aaron', - avatar: 'https://placekitten.com/50/50?image=27', - }, - { - id: 'user_28', - username: 'Bianca', - avatar: 'https://placekitten.com/50/50?image=28', - }, - { - id: 'user_29', - username: 'Carlos', - avatar: 'https://placekitten.com/50/50?image=29', - }, - { - id: 'user_30', - username: 'Diana', - avatar: 'https://placekitten.com/50/50?image=30', - }, - { - id: 'user_31', - username: 'Eli', - avatar: 'https://placekitten.com/50/50?image=31', - }, - { - id: 'user_32', - username: 'Fiona', - avatar: 'https://placekitten.com/50/50?image=32', - }, - { - id: 'user_33', - username: 'Gus', - avatar: 'https://placekitten.com/50/50?image=33', - }, - { - id: 'user_34', - username: 'Holly', - avatar: 'https://placekitten.com/50/50?image=34', - }, - { - id: 'user_35', - username: 'Ian', - avatar: 'https://placekitten.com/50/50?image=35', - }, - { - id: 'user_36', - username: 'Julia', - avatar: 'https://placekitten.com/50/50?image=36', - }, - { - id: 'user_37', - username: 'Kevin', - avatar: 'https://placekitten.com/50/50?image=37', - }, - { - id: 'user_38', - username: 'Laura', - avatar: 'https://placekitten.com/50/50?image=38', - }, - { - id: 'user_39', - username: 'Mike', - avatar: 'https://placekitten.com/50/50?image=39', - }, - { - id: 'user_40', - username: 'Nora', - avatar: 'https://placekitten.com/50/50?image=40', - }, - { - id: 'user_41', - username: 'Oliver', - avatar: 'https://placekitten.com/50/50?image=41', - }, - { - id: 'user_42', - username: 'Paula', - avatar: 'https://placekitten.com/50/50?image=42', - }, - { - id: 'user_43', - username: 'Quincy', - avatar: 'https://placekitten.com/50/50?image=43', - }, - { - id: 'user_44', - username: 'Rose', - avatar: 'https://placekitten.com/50/50?image=44', - }, - { - id: 'user_45', - username: 'Steve', - avatar: 'https://placekitten.com/50/50?image=45', - }, - { - id: 'user_46', - username: 'Tara', - avatar: 'https://placekitten.com/50/50?image=46', - }, - { - id: 'user_47', - username: 'Ulysses', - avatar: 'https://placekitten.com/50/50?image=47', - }, - { - id: 'user_48', - username: 'Violet', - avatar: 'https://placekitten.com/50/50?image=48', - }, - { - id: 'user_49', - username: 'Wes', - avatar: 'https://placekitten.com/50/50?image=49', - }, - { - id: 'user_50', - username: 'Xena', - avatar: 'https://placekitten.com/50/50?image=50', - }, - ], - verified: [ - { - id: 'user_51', - username: 'Frank', - avatar: 'https://placekitten.com/50/50?image=51', - }, - { - id: 'user_52', - username: 'Grace', - avatar: 'https://placekitten.com/50/50?image=52', - }, - { - id: 'user_53', - username: 'Henry', - avatar: 'https://placekitten.com/50/50?image=53', - }, - { - id: 'user_54', - username: 'Ivy', - avatar: 'https://placekitten.com/50/50?image=54', - }, - { - id: 'user_55', - username: 'Jack', - avatar: 'https://placekitten.com/50/50?image=55', - }, - { - id: 'user_56', - username: 'Kim', - avatar: 'https://placekitten.com/50/50?image=56', - }, - { - id: 'user_57', - username: 'Leo', - avatar: 'https://placekitten.com/50/50?image=57', - }, - { - id: 'user_58', - username: 'Mila', - avatar: 'https://placekitten.com/50/50?image=58', - }, - { - id: 'user_59', - username: 'Nate', - avatar: 'https://placekitten.com/50/50?image=59', - }, - { - id: 'user_60', - username: 'Olivia', - avatar: 'https://placekitten.com/50/50?image=60', - }, - { - id: 'user_61', - username: 'Paul', - avatar: 'https://placekitten.com/50/50?image=61', - }, - { - id: 'user_62', - username: 'Quinn', - avatar: 'https://placekitten.com/50/50?image=62', - }, - { - id: 'user_63', - username: 'Ruby', - avatar: 'https://placekitten.com/50/50?image=63', - }, - { - id: 'user_64', - username: 'Steve', - avatar: 'https://placekitten.com/50/50?image=64', - }, - { - id: 'user_65', - username: 'Tina', - avatar: 'https://placekitten.com/50/50?image=65', - }, - { - id: 'user_66', - username: 'Ulysses', - avatar: 'https://placekitten.com/50/50?image=66', - }, - { - id: 'user_67', - username: 'Vera', - avatar: 'https://placekitten.com/50/50?image=67', - }, - { - id: 'user_68', - username: 'Walter', - avatar: 'https://placekitten.com/50/50?image=68', - }, - { - id: 'user_69', - username: 'Xena', - avatar: 'https://placekitten.com/50/50?image=69', - }, - { - id: 'user_70', - username: 'Yvonne', - avatar: 'https://placekitten.com/50/50?image=70', - }, - { - id: 'user_71', - username: 'Zane', - avatar: 'https://placekitten.com/50/50?image=71', - }, - { - id: 'user_72', - username: 'Alan', - avatar: 'https://placekitten.com/50/50?image=72', - }, - { - id: 'user_73', - username: 'Bella', - avatar: 'https://placekitten.com/50/50?image=73', - }, - { - id: 'user_74', - username: 'Chris', - avatar: 'https://placekitten.com/50/50?image=74', - }, - { - id: 'user_75', - username: 'Daisy', - avatar: 'https://placekitten.com/50/50?image=75', - }, - { - id: 'user_76', - username: 'Ethan', - avatar: 'https://placekitten.com/50/50?image=76', - }, - { - id: 'user_77', - username: 'Faye', - avatar: 'https://placekitten.com/50/50?image=77', - }, - { - id: 'user_78', - username: 'Gavin', - avatar: 'https://placekitten.com/50/50?image=78', - }, - { - id: 'user_79', - username: 'Holly', - avatar: 'https://placekitten.com/50/50?image=79', - }, - { - id: 'user_80', - username: 'Isaac', - avatar: 'https://placekitten.com/50/50?image=80', - }, - { - id: 'user_81', - username: 'Julia', - avatar: 'https://placekitten.com/50/50?image=81', - }, - { - id: 'user_82', - username: 'Kevin', - avatar: 'https://placekitten.com/50/50?image=82', - }, - { - id: 'user_83', - username: 'Laura', - avatar: 'https://placekitten.com/50/50?image=83', - }, - { - id: 'user_84', - username: 'Mike', - avatar: 'https://placekitten.com/50/50?image=84', - }, - { - id: 'user_85', - username: 'Nina', - avatar: 'https://placekitten.com/50/50?image=85', - }, - { - id: 'user_86', - username: 'Oscar', - avatar: 'https://placekitten.com/50/50?image=86', - }, - { - id: 'user_87', - username: 'Pam', - avatar: 'https://placekitten.com/50/50?image=87', - }, - { - id: 'user_88', - username: 'Quincy', - avatar: 'https://placekitten.com/50/50?image=88', - }, - { - id: 'user_89', - username: 'Rose', - avatar: 'https://placekitten.com/50/50?image=89', - }, - { - id: 'user_90', - username: 'Sam', - avatar: 'https://placekitten.com/50/50?image=90', - }, - { - id: 'user_91', - username: 'Tara', - avatar: 'https://placekitten.com/50/50?image=91', - }, - { - id: 'user_92', - username: 'Uma', - avatar: 'https://placekitten.com/50/50?image=92', - }, - { - id: 'user_93', - username: 'Victor', - avatar: 'https://placekitten.com/50/50?image=93', - }, - { - id: 'user_94', - username: 'Wendy', - avatar: 'https://placekitten.com/50/50?image=94', - }, - { - id: 'user_95', - username: 'Xander', - avatar: 'https://placekitten.com/50/50?image=95', - }, - { - id: 'user_96', - username: 'Yara', - avatar: 'https://placekitten.com/50/50?image=96', - }, - { - id: 'user_97', - username: 'Zeke', - avatar: 'https://placekitten.com/50/50?image=97', - }, - { - id: 'user_98', - username: 'Ava', - avatar: 'https://placekitten.com/50/50?image=98', - }, - { - id: 'user_99', - username: 'Blake', - avatar: 'https://placekitten.com/50/50?image=99', - }, - { - id: 'user_100', - username: 'Chloe', - avatar: 'https://placekitten.com/50/50?image=100', - }, - ], -}; const tabs = [ { display_name: 'In Discord', id: 'in_discord' }, @@ -531,10 +24,13 @@ let showUser = 0; // usersData[activeTab] = await getUsers(activeTab); -const fetchUsers = async (tabId, page = 1) => { - if (isLoading) return; +export const fetchUsers = async (tabId, page = 1) => { + if (isLoading) { + return; + } isLoading = true; + try { const start = (page - 1) * INITIAL_USERS; const end = start + INITIAL_USERS; @@ -555,7 +51,7 @@ const fetchUsers = async (tabId, page = 1) => { console.log(usersData[tabId]); } currentPage = page; - rerender(App(), document.getElementById('root')); // Re-render the app with the new users + rerender(App(), document.getElementById('root')); } else { console.log('No more users to fetch'); } @@ -566,18 +62,6 @@ const fetchUsers = async (tabId, page = 1) => { } }; -// const handleScroll = () => { -// const scrollPosition = window.innerHeight + window.scrollY; -// const bottomPosition = document.body.offsetHeight - 100; // Trigger fetch 100px from bottom - -// if (scrollPosition >= bottomPosition) { -// // Fetch more users when the user is near the bottom -// fetchUsers(activeTab, currentPage + 1); -// } -// }; - -// window.addEventListener('scroll', handleScroll); - const handleTabNavigation = async (e) => { const selectedTabId = e.target.getAttribute('data_key'); if (selectedTabId) { @@ -620,6 +104,7 @@ export const App = () => { fetchUsers, activeTab, currentPage, + isLoading, }), UserDetailsSection({ user: users[showUser] ?? {} }), ]); diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index 8812d193..46cfc404 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -7,6 +7,7 @@ export const UsersSection = ({ fetchUsers, activeTab, currentPage, + isLoading, }) => { const debounce = (func, delay) => { let timeoutId; @@ -23,12 +24,17 @@ export const UsersSection = ({ debounce(() => { console.log('scroll triggered'); if (window.innerHeight + window.scrollY >= document.body.offsetHeight) { - fetchUsers(activeTab, currentPage + 1); // Fetch next page + fetchUsers(activeTab, currentPage + 1); } }, 200), ); - // handle scroll is not working - add event listener on every scroll element + if (isLoading) { + return createElement('aside', { class: 'users_section' }, [ + createElement('div', { class: 'loading' }, ['Loading...']), + ]); + } + return createElement( 'aside', { diff --git a/users/discord/utils/util.js b/users/discord/utils/util.js index 83cd40e5..6124faea 100644 --- a/users/discord/utils/util.js +++ b/users/discord/utils/util.js @@ -19,3 +19,511 @@ export const getUsers = async (tab) => { console.error(err); } }; +// mock user data +export const mockUsersData = { + in_discord: [ + { + id: 'user_1', + discordId: '123456789', + username: 'Alice', + avatar: 'https://placekitten.com/50/50?image=1', + }, + { + id: 'user_2', + username: 'Bob', + avatar: 'https://placekitten.com/50/50?image=2', + }, + { + id: 'user_3', + username: 'Charlie', + avatar: 'https://placekitten.com/50/50?image=3', + }, + { + id: 'user_4', + username: 'David', + avatar: 'https://placekitten.com/50/50?image=4', + }, + { + id: 'user_5', + username: 'Eve', + avatar: 'https://placekitten.com/50/50?image=5', + }, + { + id: 'user_6', + username: 'Fay', + avatar: 'https://placekitten.com/50/50?image=6', + }, + { + id: 'user_7', + username: 'George', + avatar: 'https://placekitten.com/50/50?image=7', + }, + { + id: 'user_8', + username: 'Hannah', + avatar: 'https://placekitten.com/50/50?image=8', + }, + { + id: 'user_9', + username: 'Isaac', + avatar: 'https://placekitten.com/50/50?image=9', + }, + { + id: 'user_10', + username: 'Jill', + avatar: 'https://placekitten.com/50/50?image=10', + }, + { + id: 'user_11', + username: 'Karl', + avatar: 'https://placekitten.com/50/50?image=11', + }, + { + id: 'user_12', + username: 'Lily', + avatar: 'https://placekitten.com/50/50?image=12', + }, + { + id: 'user_13', + username: 'Max', + avatar: 'https://placekitten.com/50/50?image=13', + }, + { + id: 'user_14', + username: 'Nina', + avatar: 'https://placekitten.com/50/50?image=14', + }, + { + id: 'user_15', + username: 'Oscar', + avatar: 'https://placekitten.com/50/50?image=15', + }, + { + id: 'user_16', + username: 'Pam', + avatar: 'https://placekitten.com/50/50?image=16', + }, + { + id: 'user_17', + username: 'Quinn', + avatar: 'https://placekitten.com/50/50?image=17', + }, + { + id: 'user_18', + username: 'Rachel', + avatar: 'https://placekitten.com/50/50?image=18', + }, + { + id: 'user_19', + username: 'Sam', + avatar: 'https://placekitten.com/50/50?image=19', + }, + { + id: 'user_20', + username: 'Tina', + avatar: 'https://placekitten.com/50/50?image=20', + }, + { + id: 'user_21', + username: 'Uma', + avatar: 'https://placekitten.com/50/50?image=21', + }, + { + id: 'user_22', + username: 'Victor', + avatar: 'https://placekitten.com/50/50?image=22', + }, + { + id: 'user_23', + username: 'Wendy', + avatar: 'https://placekitten.com/50/50?image=23', + }, + { + id: 'user_24', + username: 'Xander', + avatar: 'https://placekitten.com/50/50?image=24', + }, + { + id: 'user_25', + username: 'Yvonne', + avatar: 'https://placekitten.com/50/50?image=25', + }, + { + id: 'user_26', + username: 'Zack', + avatar: 'https://placekitten.com/50/50?image=26', + }, + { + id: 'user_27', + username: 'Aaron', + avatar: 'https://placekitten.com/50/50?image=27', + }, + { + id: 'user_28', + username: 'Bianca', + avatar: 'https://placekitten.com/50/50?image=28', + }, + { + id: 'user_29', + username: 'Carlos', + avatar: 'https://placekitten.com/50/50?image=29', + }, + { + id: 'user_30', + username: 'Diana', + avatar: 'https://placekitten.com/50/50?image=30', + }, + { + id: 'user_31', + username: 'Eli', + avatar: 'https://placekitten.com/50/50?image=31', + }, + { + id: 'user_32', + username: 'Fiona', + avatar: 'https://placekitten.com/50/50?image=32', + }, + { + id: 'user_33', + username: 'Gus', + avatar: 'https://placekitten.com/50/50?image=33', + }, + { + id: 'user_34', + username: 'Holly', + avatar: 'https://placekitten.com/50/50?image=34', + }, + { + id: 'user_35', + username: 'Ian', + avatar: 'https://placekitten.com/50/50?image=35', + }, + { + id: 'user_36', + username: 'Julia', + avatar: 'https://placekitten.com/50/50?image=36', + }, + { + id: 'user_37', + username: 'Kevin', + avatar: 'https://placekitten.com/50/50?image=37', + }, + { + id: 'user_38', + username: 'Laura', + avatar: 'https://placekitten.com/50/50?image=38', + }, + { + id: 'user_39', + username: 'Mike', + avatar: 'https://placekitten.com/50/50?image=39', + }, + { + id: 'user_40', + username: 'Nora', + avatar: 'https://placekitten.com/50/50?image=40', + }, + { + id: 'user_41', + username: 'Oliver', + avatar: 'https://placekitten.com/50/50?image=41', + }, + { + id: 'user_42', + username: 'Paula', + avatar: 'https://placekitten.com/50/50?image=42', + }, + { + id: 'user_43', + username: 'Quincy', + avatar: 'https://placekitten.com/50/50?image=43', + }, + { + id: 'user_44', + username: 'Rose', + avatar: 'https://placekitten.com/50/50?image=44', + }, + { + id: 'user_45', + username: 'Steve', + avatar: 'https://placekitten.com/50/50?image=45', + }, + { + id: 'user_46', + username: 'Tara', + avatar: 'https://placekitten.com/50/50?image=46', + }, + { + id: 'user_47', + username: 'Ulysses', + avatar: 'https://placekitten.com/50/50?image=47', + }, + { + id: 'user_48', + username: 'Violet', + avatar: 'https://placekitten.com/50/50?image=48', + }, + { + id: 'user_49', + username: 'Wes', + avatar: 'https://placekitten.com/50/50?image=49', + }, + { + id: 'user_50', + username: 'Xena', + avatar: 'https://placekitten.com/50/50?image=50', + }, + ], + verified: [ + { + id: 'user_51', + username: 'Frank', + avatar: 'https://placekitten.com/50/50?image=51', + }, + { + id: 'user_52', + username: 'Grace', + avatar: 'https://placekitten.com/50/50?image=52', + }, + { + id: 'user_53', + username: 'Henry', + avatar: 'https://placekitten.com/50/50?image=53', + }, + { + id: 'user_54', + username: 'Ivy', + avatar: 'https://placekitten.com/50/50?image=54', + }, + { + id: 'user_55', + username: 'Jack', + avatar: 'https://placekitten.com/50/50?image=55', + }, + { + id: 'user_56', + username: 'Kim', + avatar: 'https://placekitten.com/50/50?image=56', + }, + { + id: 'user_57', + username: 'Leo', + avatar: 'https://placekitten.com/50/50?image=57', + }, + { + id: 'user_58', + username: 'Mila', + avatar: 'https://placekitten.com/50/50?image=58', + }, + { + id: 'user_59', + username: 'Nate', + avatar: 'https://placekitten.com/50/50?image=59', + }, + { + id: 'user_60', + username: 'Olivia', + avatar: 'https://placekitten.com/50/50?image=60', + }, + { + id: 'user_61', + username: 'Paul', + avatar: 'https://placekitten.com/50/50?image=61', + }, + { + id: 'user_62', + username: 'Quinn', + avatar: 'https://placekitten.com/50/50?image=62', + }, + { + id: 'user_63', + username: 'Ruby', + avatar: 'https://placekitten.com/50/50?image=63', + }, + { + id: 'user_64', + username: 'Steve', + avatar: 'https://placekitten.com/50/50?image=64', + }, + { + id: 'user_65', + username: 'Tina', + avatar: 'https://placekitten.com/50/50?image=65', + }, + { + id: 'user_66', + username: 'Ulysses', + avatar: 'https://placekitten.com/50/50?image=66', + }, + { + id: 'user_67', + username: 'Vera', + avatar: 'https://placekitten.com/50/50?image=67', + }, + { + id: 'user_68', + username: 'Walter', + avatar: 'https://placekitten.com/50/50?image=68', + }, + { + id: 'user_69', + username: 'Xena', + avatar: 'https://placekitten.com/50/50?image=69', + }, + { + id: 'user_70', + username: 'Yvonne', + avatar: 'https://placekitten.com/50/50?image=70', + }, + { + id: 'user_71', + username: 'Zane', + avatar: 'https://placekitten.com/50/50?image=71', + }, + { + id: 'user_72', + username: 'Alan', + avatar: 'https://placekitten.com/50/50?image=72', + }, + { + id: 'user_73', + username: 'Bella', + avatar: 'https://placekitten.com/50/50?image=73', + }, + { + id: 'user_74', + username: 'Chris', + avatar: 'https://placekitten.com/50/50?image=74', + }, + { + id: 'user_75', + username: 'Daisy', + avatar: 'https://placekitten.com/50/50?image=75', + }, + { + id: 'user_76', + username: 'Ethan', + avatar: 'https://placekitten.com/50/50?image=76', + }, + { + id: 'user_77', + username: 'Faye', + avatar: 'https://placekitten.com/50/50?image=77', + }, + { + id: 'user_78', + username: 'Gavin', + avatar: 'https://placekitten.com/50/50?image=78', + }, + { + id: 'user_79', + username: 'Holly', + avatar: 'https://placekitten.com/50/50?image=79', + }, + { + id: 'user_80', + username: 'Isaac', + avatar: 'https://placekitten.com/50/50?image=80', + }, + { + id: 'user_81', + username: 'Julia', + avatar: 'https://placekitten.com/50/50?image=81', + }, + { + id: 'user_82', + username: 'Kevin', + avatar: 'https://placekitten.com/50/50?image=82', + }, + { + id: 'user_83', + username: 'Laura', + avatar: 'https://placekitten.com/50/50?image=83', + }, + { + id: 'user_84', + username: 'Mike', + avatar: 'https://placekitten.com/50/50?image=84', + }, + { + id: 'user_85', + username: 'Nina', + avatar: 'https://placekitten.com/50/50?image=85', + }, + { + id: 'user_86', + username: 'Oscar', + avatar: 'https://placekitten.com/50/50?image=86', + }, + { + id: 'user_87', + username: 'Pam', + avatar: 'https://placekitten.com/50/50?image=87', + }, + { + id: 'user_88', + username: 'Quincy', + avatar: 'https://placekitten.com/50/50?image=88', + }, + { + id: 'user_89', + username: 'Rose', + avatar: 'https://placekitten.com/50/50?image=89', + }, + { + id: 'user_90', + username: 'Sam', + avatar: 'https://placekitten.com/50/50?image=90', + }, + { + id: 'user_91', + username: 'Tara', + avatar: 'https://placekitten.com/50/50?image=91', + }, + { + id: 'user_92', + username: 'Uma', + avatar: 'https://placekitten.com/50/50?image=92', + }, + { + id: 'user_93', + username: 'Victor', + avatar: 'https://placekitten.com/50/50?image=93', + }, + { + id: 'user_94', + username: 'Wendy', + avatar: 'https://placekitten.com/50/50?image=94', + }, + { + id: 'user_95', + username: 'Xander', + avatar: 'https://placekitten.com/50/50?image=95', + }, + { + id: 'user_96', + username: 'Yara', + avatar: 'https://placekitten.com/50/50?image=96', + }, + { + id: 'user_97', + username: 'Zeke', + avatar: 'https://placekitten.com/50/50?image=97', + }, + { + id: 'user_98', + username: 'Ava', + avatar: 'https://placekitten.com/50/50?image=98', + }, + { + id: 'user_99', + username: 'Blake', + avatar: 'https://placekitten.com/50/50?image=99', + }, + { + id: 'user_100', + username: 'Chloe', + avatar: 'https://placekitten.com/50/50?image=100', + }, + ], +}; From 1bbfce5c179e6b4c6195e53b589be361d6dda97f Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Wed, 25 Sep 2024 10:14:16 +0530 Subject: [PATCH 07/15] added function to initially load 20 users and then load more users as we scroll, changed data fetching structure to fetch last user id --- users/discord/App.js | 29 +++++++++++++ users/discord/components/UsersSection.js | 53 +++++++++++++++--------- users/discord/style.css | 3 +- users/discord/utils/util.js | 9 +++- 4 files changed, 72 insertions(+), 22 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 87fa873d..404a5a54 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -19,8 +19,34 @@ const urlParams = new URLSearchParams(window.location.search); let activeTab = urlParams.get('tab') ?? 'in_discord'; let showUser = 0; +let isLoading = false; +const USERS_PER_FETCH = 20; + usersData[activeTab] = await getUsers(activeTab); +const fetchMoreUsers = async () => { + if (isLoading || !usersData[activeTab]) { + return; + } + isLoading = true; + const lastUserId = usersData[activeTab][usersData[activeTab].length - 1]?.id; + try { + const newUsers = await getUsers(activeTab, lastUserId, USERS_PER_FETCH); + usersData[activeTab] = [...usersData[activeTab], ...newUsers]; + isLoading = false; + rerender(App(), window['root']); + } catch (error) { + console.error('Error fetching users', error); + isLoading = false; + } +}; +const handleScroll = (e) => { + const { scrollTop, clientHeight, scrollHeight } = e.target; + if (scrollHeight - scrollTop <= clientHeight + 100) { + fetchMoreUsers(); + } +}; + const handleTabNavigation = async (e) => { const selectedTabId = e.target.getAttribute('data_key'); if (selectedTabId) { @@ -60,6 +86,8 @@ export const App = () => { users, showUser, handleUserSelected, + handleScroll, + isLoading, }), UserDetailsSection({ user: users[showUser] ?? {} }), ]); @@ -69,3 +97,4 @@ export const App = () => { NoUserFound(), ]); }; +fetchMoreUsers(); diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index bc07cdaa..b55cd28e 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -1,26 +1,39 @@ const { createElement } = react; -export const UsersSection = ({ users, showUser, handleUserSelected }) => { +export const UsersSection = ({ + users, + showUser, + handleUserSelected, + handleScroll, + isLoading, +}) => { return createElement( 'aside', - { class: 'users_section', onclick: handleUserSelected }, - users?.map((user) => { - return createElement( - 'div', - { - class: `user_card ${ - users[showUser].id === user.id ? 'active_tab' : '' - }`, - data_key: user.id, - }, - [ - createElement('img', { - src: user?.picture?.url ?? dummyPicture, - class: 'user_image', - }), - createElement('span', {}, [user.first_name + ' ' + user.last_name]), - ], - ); - }), + { + class: 'users_section', + onclick: handleUserSelected, + onscroll: handleScroll, + }, + [ + ...users?.map((user) => { + return createElement( + 'div', + { + class: `user_card ${ + users[showUser].id === user.id ? 'active_tab' : '' + }`, + data_key: user.id, + }, + [ + createElement('img', { + src: user?.picture?.url ?? dummyPicture, + class: 'user_image', + }), + createElement('span', {}, [user.first_name + ' ' + user.last_name]), + ], + ); + }), + isLoading && createElement('div', 'Load more users...'), + ], ); }; diff --git a/users/discord/style.css b/users/discord/style.css index 23058547..f71d7a51 100644 --- a/users/discord/style.css +++ b/users/discord/style.css @@ -19,8 +19,9 @@ main { .users_section { grid-area: aside; - overflow: scroll; + overflow: auto; padding-inline: 1rem; + max-height: 80vh; } .tabs_section { diff --git a/users/discord/utils/util.js b/users/discord/utils/util.js index 83cd40e5..649162f5 100644 --- a/users/discord/utils/util.js +++ b/users/discord/utils/util.js @@ -1,8 +1,12 @@ -export const getUsers = async (tab) => { +export const getUsers = async (tab, lastUserId = null, limit = 20) => { let URL = { in_discord: `${API_BASE_URL}/users/search/?role=in_discord`, verified: `${API_BASE_URL}/users/search/?verified=true`, }; + if (lastUserId) { + URL[tab] += `&last_id=${lastUserId}`; + } + URL[tab] += `&limit=${limit}`; try { const response = await fetch(URL[tab], { @@ -12,6 +16,9 @@ export const getUsers = async (tab) => { 'Content-type': 'application/json', }, }); + if (!response.ok) { + console.error('Failed to fetch:', response.status, response.statusText); + } const data = await response.json(); return data.users ?? []; From e9ffa537ade28480d6d9afb7dafe9579891d23ec Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Tue, 8 Oct 2024 21:30:38 +0530 Subject: [PATCH 08/15] fetching mock users and handling fetch more users --- users/discord/App.js | 562 +++++++++++++++++++++-- users/discord/components/UsersSection.js | 58 ++- users/discord/utils/util.js | 9 +- 3 files changed, 572 insertions(+), 57 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 404a5a54..22a928fc 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -5,6 +5,518 @@ import { getUsers } from './utils/util.js'; import { NoUserFound } from './components/NoUserFound.js'; const { createElement, rerender } = react; +const mockUsersData = { + in_discord: [ + { + id: 'user_1', + discordId: '123456789', + username: 'Alice', + avatar: 'https://placekitten.com/50/50?image=1', + }, + { + id: 'user_2', + username: 'Bob', + avatar: 'https://placekitten.com/50/50?image=2', + }, + { + id: 'user_3', + username: 'Charlie', + avatar: 'https://placekitten.com/50/50?image=3', + }, + { + id: 'user_4', + username: 'David', + avatar: 'https://placekitten.com/50/50?image=4', + }, + { + id: 'user_5', + username: 'Eve', + avatar: 'https://placekitten.com/50/50?image=5', + }, + { + id: 'user_6', + username: 'Fay', + avatar: 'https://placekitten.com/50/50?image=6', + }, + { + id: 'user_7', + username: 'George', + avatar: 'https://placekitten.com/50/50?image=7', + }, + { + id: 'user_8', + username: 'Hannah', + avatar: 'https://placekitten.com/50/50?image=8', + }, + { + id: 'user_9', + username: 'Isaac', + avatar: 'https://placekitten.com/50/50?image=9', + }, + { + id: 'user_10', + username: 'Jill', + avatar: 'https://placekitten.com/50/50?image=10', + }, + { + id: 'user_11', + username: 'Karl', + avatar: 'https://placekitten.com/50/50?image=11', + }, + { + id: 'user_12', + username: 'Lily', + avatar: 'https://placekitten.com/50/50?image=12', + }, + { + id: 'user_13', + username: 'Max', + avatar: 'https://placekitten.com/50/50?image=13', + }, + { + id: 'user_14', + username: 'Nina', + avatar: 'https://placekitten.com/50/50?image=14', + }, + { + id: 'user_15', + username: 'Oscar', + avatar: 'https://placekitten.com/50/50?image=15', + }, + { + id: 'user_16', + username: 'Pam', + avatar: 'https://placekitten.com/50/50?image=16', + }, + { + id: 'user_17', + username: 'Quinn', + avatar: 'https://placekitten.com/50/50?image=17', + }, + { + id: 'user_18', + username: 'Rachel', + avatar: 'https://placekitten.com/50/50?image=18', + }, + { + id: 'user_19', + username: 'Sam', + avatar: 'https://placekitten.com/50/50?image=19', + }, + { + id: 'user_20', + username: 'Tina', + avatar: 'https://placekitten.com/50/50?image=20', + }, + { + id: 'user_21', + username: 'Uma', + avatar: 'https://placekitten.com/50/50?image=21', + }, + { + id: 'user_22', + username: 'Victor', + avatar: 'https://placekitten.com/50/50?image=22', + }, + { + id: 'user_23', + username: 'Wendy', + avatar: 'https://placekitten.com/50/50?image=23', + }, + { + id: 'user_24', + username: 'Xander', + avatar: 'https://placekitten.com/50/50?image=24', + }, + { + id: 'user_25', + username: 'Yvonne', + avatar: 'https://placekitten.com/50/50?image=25', + }, + { + id: 'user_26', + username: 'Zack', + avatar: 'https://placekitten.com/50/50?image=26', + }, + { + id: 'user_27', + username: 'Aaron', + avatar: 'https://placekitten.com/50/50?image=27', + }, + { + id: 'user_28', + username: 'Bianca', + avatar: 'https://placekitten.com/50/50?image=28', + }, + { + id: 'user_29', + username: 'Carlos', + avatar: 'https://placekitten.com/50/50?image=29', + }, + { + id: 'user_30', + username: 'Diana', + avatar: 'https://placekitten.com/50/50?image=30', + }, + { + id: 'user_31', + username: 'Eli', + avatar: 'https://placekitten.com/50/50?image=31', + }, + { + id: 'user_32', + username: 'Fiona', + avatar: 'https://placekitten.com/50/50?image=32', + }, + { + id: 'user_33', + username: 'Gus', + avatar: 'https://placekitten.com/50/50?image=33', + }, + { + id: 'user_34', + username: 'Holly', + avatar: 'https://placekitten.com/50/50?image=34', + }, + { + id: 'user_35', + username: 'Ian', + avatar: 'https://placekitten.com/50/50?image=35', + }, + { + id: 'user_36', + username: 'Julia', + avatar: 'https://placekitten.com/50/50?image=36', + }, + { + id: 'user_37', + username: 'Kevin', + avatar: 'https://placekitten.com/50/50?image=37', + }, + { + id: 'user_38', + username: 'Laura', + avatar: 'https://placekitten.com/50/50?image=38', + }, + { + id: 'user_39', + username: 'Mike', + avatar: 'https://placekitten.com/50/50?image=39', + }, + { + id: 'user_40', + username: 'Nora', + avatar: 'https://placekitten.com/50/50?image=40', + }, + { + id: 'user_41', + username: 'Oliver', + avatar: 'https://placekitten.com/50/50?image=41', + }, + { + id: 'user_42', + username: 'Paula', + avatar: 'https://placekitten.com/50/50?image=42', + }, + { + id: 'user_43', + username: 'Quincy', + avatar: 'https://placekitten.com/50/50?image=43', + }, + { + id: 'user_44', + username: 'Rose', + avatar: 'https://placekitten.com/50/50?image=44', + }, + { + id: 'user_45', + username: 'Steve', + avatar: 'https://placekitten.com/50/50?image=45', + }, + { + id: 'user_46', + username: 'Tara', + avatar: 'https://placekitten.com/50/50?image=46', + }, + { + id: 'user_47', + username: 'Ulysses', + avatar: 'https://placekitten.com/50/50?image=47', + }, + { + id: 'user_48', + username: 'Violet', + avatar: 'https://placekitten.com/50/50?image=48', + }, + { + id: 'user_49', + username: 'Wes', + avatar: 'https://placekitten.com/50/50?image=49', + }, + { + id: 'user_50', + username: 'Xena', + avatar: 'https://placekitten.com/50/50?image=50', + }, + ], + verified: [ + { + id: 'user_51', + username: 'Frank', + avatar: 'https://placekitten.com/50/50?image=51', + }, + { + id: 'user_52', + username: 'Grace', + avatar: 'https://placekitten.com/50/50?image=52', + }, + { + id: 'user_53', + username: 'Henry', + avatar: 'https://placekitten.com/50/50?image=53', + }, + { + id: 'user_54', + username: 'Ivy', + avatar: 'https://placekitten.com/50/50?image=54', + }, + { + id: 'user_55', + username: 'Jack', + avatar: 'https://placekitten.com/50/50?image=55', + }, + { + id: 'user_56', + username: 'Kim', + avatar: 'https://placekitten.com/50/50?image=56', + }, + { + id: 'user_57', + username: 'Leo', + avatar: 'https://placekitten.com/50/50?image=57', + }, + { + id: 'user_58', + username: 'Mila', + avatar: 'https://placekitten.com/50/50?image=58', + }, + { + id: 'user_59', + username: 'Nate', + avatar: 'https://placekitten.com/50/50?image=59', + }, + { + id: 'user_60', + username: 'Olivia', + avatar: 'https://placekitten.com/50/50?image=60', + }, + { + id: 'user_61', + username: 'Paul', + avatar: 'https://placekitten.com/50/50?image=61', + }, + { + id: 'user_62', + username: 'Quinn', + avatar: 'https://placekitten.com/50/50?image=62', + }, + { + id: 'user_63', + username: 'Ruby', + avatar: 'https://placekitten.com/50/50?image=63', + }, + { + id: 'user_64', + username: 'Steve', + avatar: 'https://placekitten.com/50/50?image=64', + }, + { + id: 'user_65', + username: 'Tina', + avatar: 'https://placekitten.com/50/50?image=65', + }, + { + id: 'user_66', + username: 'Ulysses', + avatar: 'https://placekitten.com/50/50?image=66', + }, + { + id: 'user_67', + username: 'Vera', + avatar: 'https://placekitten.com/50/50?image=67', + }, + { + id: 'user_68', + username: 'Walter', + avatar: 'https://placekitten.com/50/50?image=68', + }, + { + id: 'user_69', + username: 'Xena', + avatar: 'https://placekitten.com/50/50?image=69', + }, + { + id: 'user_70', + username: 'Yvonne', + avatar: 'https://placekitten.com/50/50?image=70', + }, + { + id: 'user_71', + username: 'Zane', + avatar: 'https://placekitten.com/50/50?image=71', + }, + { + id: 'user_72', + username: 'Alan', + avatar: 'https://placekitten.com/50/50?image=72', + }, + { + id: 'user_73', + username: 'Bella', + avatar: 'https://placekitten.com/50/50?image=73', + }, + { + id: 'user_74', + username: 'Chris', + avatar: 'https://placekitten.com/50/50?image=74', + }, + { + id: 'user_75', + username: 'Daisy', + avatar: 'https://placekitten.com/50/50?image=75', + }, + { + id: 'user_76', + username: 'Ethan', + avatar: 'https://placekitten.com/50/50?image=76', + }, + { + id: 'user_77', + username: 'Faye', + avatar: 'https://placekitten.com/50/50?image=77', + }, + { + id: 'user_78', + username: 'Gavin', + avatar: 'https://placekitten.com/50/50?image=78', + }, + { + id: 'user_79', + username: 'Holly', + avatar: 'https://placekitten.com/50/50?image=79', + }, + { + id: 'user_80', + username: 'Isaac', + avatar: 'https://placekitten.com/50/50?image=80', + }, + { + id: 'user_81', + username: 'Julia', + avatar: 'https://placekitten.com/50/50?image=81', + }, + { + id: 'user_82', + username: 'Kevin', + avatar: 'https://placekitten.com/50/50?image=82', + }, + { + id: 'user_83', + username: 'Laura', + avatar: 'https://placekitten.com/50/50?image=83', + }, + { + id: 'user_84', + username: 'Mike', + avatar: 'https://placekitten.com/50/50?image=84', + }, + { + id: 'user_85', + username: 'Nina', + avatar: 'https://placekitten.com/50/50?image=85', + }, + { + id: 'user_86', + username: 'Oscar', + avatar: 'https://placekitten.com/50/50?image=86', + }, + { + id: 'user_87', + username: 'Pam', + avatar: 'https://placekitten.com/50/50?image=87', + }, + { + id: 'user_88', + username: 'Quincy', + avatar: 'https://placekitten.com/50/50?image=88', + }, + { + id: 'user_89', + username: 'Rose', + avatar: 'https://placekitten.com/50/50?image=89', + }, + { + id: 'user_90', + username: 'Sam', + avatar: 'https://placekitten.com/50/50?image=90', + }, + { + id: 'user_91', + username: 'Tara', + avatar: 'https://placekitten.com/50/50?image=91', + }, + { + id: 'user_92', + username: 'Uma', + avatar: 'https://placekitten.com/50/50?image=92', + }, + { + id: 'user_93', + username: 'Victor', + avatar: 'https://placekitten.com/50/50?image=93', + }, + { + id: 'user_94', + username: 'Wendy', + avatar: 'https://placekitten.com/50/50?image=94', + }, + { + id: 'user_95', + username: 'Xander', + avatar: 'https://placekitten.com/50/50?image=95', + }, + { + id: 'user_96', + username: 'Yara', + avatar: 'https://placekitten.com/50/50?image=96', + }, + { + id: 'user_97', + username: 'Zeke', + avatar: 'https://placekitten.com/50/50?image=97', + }, + { + id: 'user_98', + username: 'Ava', + avatar: 'https://placekitten.com/50/50?image=98', + }, + { + id: 'user_99', + username: 'Blake', + avatar: 'https://placekitten.com/50/50?image=99', + }, + { + id: 'user_100', + username: 'Chloe', + avatar: 'https://placekitten.com/50/50?image=100', + }, + ], +}; +/* work on pagination with array index for now, forget about last user id. +You should call the API every time the user reaches the end of the page. +Let's say initially you load 10 users- that's index 0,9 then when the user, +reaches bottom of the page you fetch the data again to get the next 10 users- that's index 10,19 +*/ const tabs = [ { display_name: 'In Discord', id: 'in_discord' }, @@ -17,34 +529,34 @@ export const usersData = { const urlParams = new URLSearchParams(window.location.search); let activeTab = urlParams.get('tab') ?? 'in_discord'; - -let showUser = 0; +const INITIAL_USERS = 10; let isLoading = false; -const USERS_PER_FETCH = 20; +let currentPage = 1; +let showUser = 0; +// get mock users +const getMockUser = (tabId, page = 1) => { + const start = (page - 1) * INITIAL_USERS; + const end = start + INITIAL_USERS; + console.log('fetched initial users'); + // currentPage++; + return mockUsersData[tabId].slice(start, end); +}; + +// usersData[activeTab] = await getUsers(activeTab); + +usersData[activeTab] = await getMockUser(activeTab); -usersData[activeTab] = await getUsers(activeTab); +/* create a function to fetch more users (for eg. we initially have 6 users, +we fetch users everytime the user reaches the end of the page.) */ const fetchMoreUsers = async () => { - if (isLoading || !usersData[activeTab]) { - return; - } isLoading = true; - const lastUserId = usersData[activeTab][usersData[activeTab].length - 1]?.id; - try { - const newUsers = await getUsers(activeTab, lastUserId, USERS_PER_FETCH); - usersData[activeTab] = [...usersData[activeTab], ...newUsers]; - isLoading = false; - rerender(App(), window['root']); - } catch (error) { - console.error('Error fetching users', error); - isLoading = false; - } -}; -const handleScroll = (e) => { - const { scrollTop, clientHeight, scrollHeight } = e.target; - if (scrollHeight - scrollTop <= clientHeight + 100) { - fetchMoreUsers(); - } + currentPage++; + const newUsers = await getMockUser(activeTab, currentPage); + usersData[activeTab] = [...usersData[activeTab], ...newUsers]; + console.log(newUsers, 'fetched new users'); + + isLoading = false; }; const handleTabNavigation = async (e) => { @@ -86,8 +598,7 @@ export const App = () => { users, showUser, handleUserSelected, - handleScroll, - isLoading, + fetchMoreUsers, }), UserDetailsSection({ user: users[showUser] ?? {} }), ]); @@ -97,4 +608,3 @@ export const App = () => { NoUserFound(), ]); }; -fetchMoreUsers(); diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index b55cd28e..70f7d8bd 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -4,9 +4,21 @@ export const UsersSection = ({ users, showUser, handleUserSelected, - handleScroll, - isLoading, + fetchMoreUsers, }) => { + const handleScroll = (e) => { + console.log('scroll triggered'); + + const container = e.target; + const { scrollTop, scrollHeight, clientHeight } = container; + if (scrollTop + clientHeight >= scrollHeight - 5) { + isLoading = true; + console.log('user scrolling'); + fetchMoreUsers(); + } + }; + + // handle scroll is not working - add event listener on every scroll element return createElement( 'aside', { @@ -14,26 +26,26 @@ export const UsersSection = ({ onclick: handleUserSelected, onscroll: handleScroll, }, - [ - ...users?.map((user) => { - return createElement( - 'div', - { - class: `user_card ${ - users[showUser].id === user.id ? 'active_tab' : '' - }`, - data_key: user.id, - }, - [ - createElement('img', { - src: user?.picture?.url ?? dummyPicture, - class: 'user_image', - }), - createElement('span', {}, [user.first_name + ' ' + user.last_name]), - ], - ); - }), - isLoading && createElement('div', 'Load more users...'), - ], + users?.map((user) => { + return createElement( + 'div', + { + class: `user_card ${ + users[showUser].id === user.id ? 'active_tab' : '' + }`, + data_key: user.id, + }, + [ + createElement('img', { + src: user?.picture?.url ?? dummyPicture, + class: 'user_image', + }), + // createElement('span', {}, [ + // user.first_name + ' ' + user.last_name + user.username, + // ]), + createElement('span', {}, [user.username]), + ], + ); + }), ); }; diff --git a/users/discord/utils/util.js b/users/discord/utils/util.js index 649162f5..83cd40e5 100644 --- a/users/discord/utils/util.js +++ b/users/discord/utils/util.js @@ -1,12 +1,8 @@ -export const getUsers = async (tab, lastUserId = null, limit = 20) => { +export const getUsers = async (tab) => { let URL = { in_discord: `${API_BASE_URL}/users/search/?role=in_discord`, verified: `${API_BASE_URL}/users/search/?verified=true`, }; - if (lastUserId) { - URL[tab] += `&last_id=${lastUserId}`; - } - URL[tab] += `&limit=${limit}`; try { const response = await fetch(URL[tab], { @@ -16,9 +12,6 @@ export const getUsers = async (tab, lastUserId = null, limit = 20) => { 'Content-type': 'application/json', }, }); - if (!response.ok) { - console.error('Failed to fetch:', response.status, response.statusText); - } const data = await response.json(); return data.users ?? []; From eb8e8fa47a2ce41f26bf88386d5af9e061015a7c Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Thu, 10 Oct 2024 20:29:04 +0530 Subject: [PATCH 09/15] users are getting fetched with scroll but the next set of users are not visible in screen --- users/discord/App.js | 67 +++++++++++++++--------- users/discord/components/UsersSection.js | 33 +++++++----- 2 files changed, 64 insertions(+), 36 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 22a928fc..438f89b8 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -512,11 +512,6 @@ const mockUsersData = { }, ], }; -/* work on pagination with array index for now, forget about last user id. -You should call the API every time the user reaches the end of the page. -Let's say initially you load 10 users- that's index 0,9 then when the user, -reaches bottom of the page you fetch the data again to get the next 10 users- that's index 10,19 -*/ const tabs = [ { display_name: 'In Discord', id: 'in_discord' }, @@ -533,32 +528,52 @@ const INITIAL_USERS = 10; let isLoading = false; let currentPage = 1; let showUser = 0; -// get mock users -const getMockUser = (tabId, page = 1) => { - const start = (page - 1) * INITIAL_USERS; - const end = start + INITIAL_USERS; - console.log('fetched initial users'); - // currentPage++; - return mockUsersData[tabId].slice(start, end); -}; // usersData[activeTab] = await getUsers(activeTab); -usersData[activeTab] = await getMockUser(activeTab); - -/* create a function to fetch more users (for eg. we initially have 6 users, -we fetch users everytime the user reaches the end of the page.) */ +const fetchUsers = async (tabId, page = 1) => { + if (isLoading) return; -const fetchMoreUsers = async () => { isLoading = true; - currentPage++; - const newUsers = await getMockUser(activeTab, currentPage); - usersData[activeTab] = [...usersData[activeTab], ...newUsers]; - console.log(newUsers, 'fetched new users'); + try { + const start = (page - 1) * INITIAL_USERS; + const end = start + INITIAL_USERS; + + const newUsers = mockUsersData[tabId].slice(start, end); - isLoading = false; + if (newUsers.length > 0) { + if (page === 1) { + usersData[tabId] = newUsers; // Initial load + console.log('Fetched initial users'); + } else { + usersData[tabId] = [...usersData[tabId], ...newUsers]; // Append new users + console.log('Fetched more users'); + console.log(usersData[tabId]); + } + currentPage = page; + rerender(App(), window[root]); // Re-render the app with the new users + } else { + console.log('No more users to fetch'); + } + } catch (error) { + console.error('Error fetching users', error); + } finally { + isLoading = false; + } }; +const handleScroll = () => { + const scrollPosition = window.innerHeight + window.scrollY; + const bottomPosition = document.body.offsetHeight - 100; // Trigger fetch 100px from bottom + + if (scrollPosition >= bottomPosition) { + // Fetch more users when the user is near the bottom + fetchUsers(activeTab, currentPage + 1); + } +}; + +window.addEventListener('scroll', handleScroll); + const handleTabNavigation = async (e) => { const selectedTabId = e.target.getAttribute('data_key'); if (selectedTabId) { @@ -598,7 +613,9 @@ export const App = () => { users, showUser, handleUserSelected, - fetchMoreUsers, + fetchUsers, + activeTab, + currentPage, }), UserDetailsSection({ user: users[showUser] ?? {} }), ]); @@ -608,3 +625,5 @@ export const App = () => { NoUserFound(), ]); }; + +fetchUsers(activeTab, 1); diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index 70f7d8bd..8812d193 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -4,27 +4,36 @@ export const UsersSection = ({ users, showUser, handleUserSelected, - fetchMoreUsers, + fetchUsers, + activeTab, + currentPage, }) => { - const handleScroll = (e) => { - console.log('scroll triggered'); - - const container = e.target; - const { scrollTop, scrollHeight, clientHeight } = container; - if (scrollTop + clientHeight >= scrollHeight - 5) { - isLoading = true; - console.log('user scrolling'); - fetchMoreUsers(); - } + const debounce = (func, delay) => { + let timeoutId; + return function (...args) { + clearTimeout(timeoutId); + timeoutId = setTimeout(() => { + func.apply(this, args); + }, delay); + }; }; + window.addEventListener( + 'scroll', + debounce(() => { + console.log('scroll triggered'); + if (window.innerHeight + window.scrollY >= document.body.offsetHeight) { + fetchUsers(activeTab, currentPage + 1); // Fetch next page + } + }, 200), + ); + // handle scroll is not working - add event listener on every scroll element return createElement( 'aside', { class: 'users_section', onclick: handleUserSelected, - onscroll: handleScroll, }, users?.map((user) => { return createElement( From 87ec1d99f75e8e68715bd97b7482da1459429db4 Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Tue, 15 Oct 2024 07:08:38 +0530 Subject: [PATCH 10/15] user list is getting updated --- users/discord/App.js | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 438f89b8..2f3100a4 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -551,7 +551,7 @@ const fetchUsers = async (tabId, page = 1) => { console.log(usersData[tabId]); } currentPage = page; - rerender(App(), window[root]); // Re-render the app with the new users + rerender(App(), document.getElementById('root')); // Re-render the app with the new users } else { console.log('No more users to fetch'); } @@ -562,17 +562,17 @@ const fetchUsers = async (tabId, page = 1) => { } }; -const handleScroll = () => { - const scrollPosition = window.innerHeight + window.scrollY; - const bottomPosition = document.body.offsetHeight - 100; // Trigger fetch 100px from bottom +// const handleScroll = () => { +// const scrollPosition = window.innerHeight + window.scrollY; +// const bottomPosition = document.body.offsetHeight - 100; // Trigger fetch 100px from bottom - if (scrollPosition >= bottomPosition) { - // Fetch more users when the user is near the bottom - fetchUsers(activeTab, currentPage + 1); - } -}; +// if (scrollPosition >= bottomPosition) { +// // Fetch more users when the user is near the bottom +// fetchUsers(activeTab, currentPage + 1); +// } +// }; -window.addEventListener('scroll', handleScroll); +// window.addEventListener('scroll', handleScroll); const handleTabNavigation = async (e) => { const selectedTabId = e.target.getAttribute('data_key'); From 458cb095c3babf264737ef680333fc295a3d85bb Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Tue, 15 Oct 2024 07:23:44 +0530 Subject: [PATCH 11/15] fixed duplicated fetching --- users/discord/App.js | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/users/discord/App.js b/users/discord/App.js index 2f3100a4..2293ccf4 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -546,7 +546,11 @@ const fetchUsers = async (tabId, page = 1) => { usersData[tabId] = newUsers; // Initial load console.log('Fetched initial users'); } else { - usersData[tabId] = [...usersData[tabId], ...newUsers]; // Append new users + const existingIds = new Set(usersData[tabId].map((user) => user.id)); + const uniqueNewUsers = newUsers.filter( + (user) => !existingIds.has(user.id), + ); + usersData[tabId] = [...usersData[tabId], ...uniqueNewUsers]; console.log('Fetched more users'); console.log(usersData[tabId]); } From de294ea6bb62ddb7f0473dfcf44f5d716f8a0637 Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Tue, 15 Oct 2024 19:31:36 +0530 Subject: [PATCH 12/15] moved mock data to utils, addded loading state --- users/discord/App.js | 531 +---------------------- users/discord/components/UsersSection.js | 10 +- users/discord/utils/util.js | 508 ++++++++++++++++++++++ 3 files changed, 524 insertions(+), 525 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 2293ccf4..73aeda96 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -1,517 +1,10 @@ import { TabsSection } from './components/TabsSection.js'; import { UsersSection } from './components/UsersSection.js'; import { UserDetailsSection } from './components/UserDetailsSection.js'; -import { getUsers } from './utils/util.js'; +import { getUsers, mockUsersData } from './utils/util.js'; import { NoUserFound } from './components/NoUserFound.js'; const { createElement, rerender } = react; -const mockUsersData = { - in_discord: [ - { - id: 'user_1', - discordId: '123456789', - username: 'Alice', - avatar: 'https://placekitten.com/50/50?image=1', - }, - { - id: 'user_2', - username: 'Bob', - avatar: 'https://placekitten.com/50/50?image=2', - }, - { - id: 'user_3', - username: 'Charlie', - avatar: 'https://placekitten.com/50/50?image=3', - }, - { - id: 'user_4', - username: 'David', - avatar: 'https://placekitten.com/50/50?image=4', - }, - { - id: 'user_5', - username: 'Eve', - avatar: 'https://placekitten.com/50/50?image=5', - }, - { - id: 'user_6', - username: 'Fay', - avatar: 'https://placekitten.com/50/50?image=6', - }, - { - id: 'user_7', - username: 'George', - avatar: 'https://placekitten.com/50/50?image=7', - }, - { - id: 'user_8', - username: 'Hannah', - avatar: 'https://placekitten.com/50/50?image=8', - }, - { - id: 'user_9', - username: 'Isaac', - avatar: 'https://placekitten.com/50/50?image=9', - }, - { - id: 'user_10', - username: 'Jill', - avatar: 'https://placekitten.com/50/50?image=10', - }, - { - id: 'user_11', - username: 'Karl', - avatar: 'https://placekitten.com/50/50?image=11', - }, - { - id: 'user_12', - username: 'Lily', - avatar: 'https://placekitten.com/50/50?image=12', - }, - { - id: 'user_13', - username: 'Max', - avatar: 'https://placekitten.com/50/50?image=13', - }, - { - id: 'user_14', - username: 'Nina', - avatar: 'https://placekitten.com/50/50?image=14', - }, - { - id: 'user_15', - username: 'Oscar', - avatar: 'https://placekitten.com/50/50?image=15', - }, - { - id: 'user_16', - username: 'Pam', - avatar: 'https://placekitten.com/50/50?image=16', - }, - { - id: 'user_17', - username: 'Quinn', - avatar: 'https://placekitten.com/50/50?image=17', - }, - { - id: 'user_18', - username: 'Rachel', - avatar: 'https://placekitten.com/50/50?image=18', - }, - { - id: 'user_19', - username: 'Sam', - avatar: 'https://placekitten.com/50/50?image=19', - }, - { - id: 'user_20', - username: 'Tina', - avatar: 'https://placekitten.com/50/50?image=20', - }, - { - id: 'user_21', - username: 'Uma', - avatar: 'https://placekitten.com/50/50?image=21', - }, - { - id: 'user_22', - username: 'Victor', - avatar: 'https://placekitten.com/50/50?image=22', - }, - { - id: 'user_23', - username: 'Wendy', - avatar: 'https://placekitten.com/50/50?image=23', - }, - { - id: 'user_24', - username: 'Xander', - avatar: 'https://placekitten.com/50/50?image=24', - }, - { - id: 'user_25', - username: 'Yvonne', - avatar: 'https://placekitten.com/50/50?image=25', - }, - { - id: 'user_26', - username: 'Zack', - avatar: 'https://placekitten.com/50/50?image=26', - }, - { - id: 'user_27', - username: 'Aaron', - avatar: 'https://placekitten.com/50/50?image=27', - }, - { - id: 'user_28', - username: 'Bianca', - avatar: 'https://placekitten.com/50/50?image=28', - }, - { - id: 'user_29', - username: 'Carlos', - avatar: 'https://placekitten.com/50/50?image=29', - }, - { - id: 'user_30', - username: 'Diana', - avatar: 'https://placekitten.com/50/50?image=30', - }, - { - id: 'user_31', - username: 'Eli', - avatar: 'https://placekitten.com/50/50?image=31', - }, - { - id: 'user_32', - username: 'Fiona', - avatar: 'https://placekitten.com/50/50?image=32', - }, - { - id: 'user_33', - username: 'Gus', - avatar: 'https://placekitten.com/50/50?image=33', - }, - { - id: 'user_34', - username: 'Holly', - avatar: 'https://placekitten.com/50/50?image=34', - }, - { - id: 'user_35', - username: 'Ian', - avatar: 'https://placekitten.com/50/50?image=35', - }, - { - id: 'user_36', - username: 'Julia', - avatar: 'https://placekitten.com/50/50?image=36', - }, - { - id: 'user_37', - username: 'Kevin', - avatar: 'https://placekitten.com/50/50?image=37', - }, - { - id: 'user_38', - username: 'Laura', - avatar: 'https://placekitten.com/50/50?image=38', - }, - { - id: 'user_39', - username: 'Mike', - avatar: 'https://placekitten.com/50/50?image=39', - }, - { - id: 'user_40', - username: 'Nora', - avatar: 'https://placekitten.com/50/50?image=40', - }, - { - id: 'user_41', - username: 'Oliver', - avatar: 'https://placekitten.com/50/50?image=41', - }, - { - id: 'user_42', - username: 'Paula', - avatar: 'https://placekitten.com/50/50?image=42', - }, - { - id: 'user_43', - username: 'Quincy', - avatar: 'https://placekitten.com/50/50?image=43', - }, - { - id: 'user_44', - username: 'Rose', - avatar: 'https://placekitten.com/50/50?image=44', - }, - { - id: 'user_45', - username: 'Steve', - avatar: 'https://placekitten.com/50/50?image=45', - }, - { - id: 'user_46', - username: 'Tara', - avatar: 'https://placekitten.com/50/50?image=46', - }, - { - id: 'user_47', - username: 'Ulysses', - avatar: 'https://placekitten.com/50/50?image=47', - }, - { - id: 'user_48', - username: 'Violet', - avatar: 'https://placekitten.com/50/50?image=48', - }, - { - id: 'user_49', - username: 'Wes', - avatar: 'https://placekitten.com/50/50?image=49', - }, - { - id: 'user_50', - username: 'Xena', - avatar: 'https://placekitten.com/50/50?image=50', - }, - ], - verified: [ - { - id: 'user_51', - username: 'Frank', - avatar: 'https://placekitten.com/50/50?image=51', - }, - { - id: 'user_52', - username: 'Grace', - avatar: 'https://placekitten.com/50/50?image=52', - }, - { - id: 'user_53', - username: 'Henry', - avatar: 'https://placekitten.com/50/50?image=53', - }, - { - id: 'user_54', - username: 'Ivy', - avatar: 'https://placekitten.com/50/50?image=54', - }, - { - id: 'user_55', - username: 'Jack', - avatar: 'https://placekitten.com/50/50?image=55', - }, - { - id: 'user_56', - username: 'Kim', - avatar: 'https://placekitten.com/50/50?image=56', - }, - { - id: 'user_57', - username: 'Leo', - avatar: 'https://placekitten.com/50/50?image=57', - }, - { - id: 'user_58', - username: 'Mila', - avatar: 'https://placekitten.com/50/50?image=58', - }, - { - id: 'user_59', - username: 'Nate', - avatar: 'https://placekitten.com/50/50?image=59', - }, - { - id: 'user_60', - username: 'Olivia', - avatar: 'https://placekitten.com/50/50?image=60', - }, - { - id: 'user_61', - username: 'Paul', - avatar: 'https://placekitten.com/50/50?image=61', - }, - { - id: 'user_62', - username: 'Quinn', - avatar: 'https://placekitten.com/50/50?image=62', - }, - { - id: 'user_63', - username: 'Ruby', - avatar: 'https://placekitten.com/50/50?image=63', - }, - { - id: 'user_64', - username: 'Steve', - avatar: 'https://placekitten.com/50/50?image=64', - }, - { - id: 'user_65', - username: 'Tina', - avatar: 'https://placekitten.com/50/50?image=65', - }, - { - id: 'user_66', - username: 'Ulysses', - avatar: 'https://placekitten.com/50/50?image=66', - }, - { - id: 'user_67', - username: 'Vera', - avatar: 'https://placekitten.com/50/50?image=67', - }, - { - id: 'user_68', - username: 'Walter', - avatar: 'https://placekitten.com/50/50?image=68', - }, - { - id: 'user_69', - username: 'Xena', - avatar: 'https://placekitten.com/50/50?image=69', - }, - { - id: 'user_70', - username: 'Yvonne', - avatar: 'https://placekitten.com/50/50?image=70', - }, - { - id: 'user_71', - username: 'Zane', - avatar: 'https://placekitten.com/50/50?image=71', - }, - { - id: 'user_72', - username: 'Alan', - avatar: 'https://placekitten.com/50/50?image=72', - }, - { - id: 'user_73', - username: 'Bella', - avatar: 'https://placekitten.com/50/50?image=73', - }, - { - id: 'user_74', - username: 'Chris', - avatar: 'https://placekitten.com/50/50?image=74', - }, - { - id: 'user_75', - username: 'Daisy', - avatar: 'https://placekitten.com/50/50?image=75', - }, - { - id: 'user_76', - username: 'Ethan', - avatar: 'https://placekitten.com/50/50?image=76', - }, - { - id: 'user_77', - username: 'Faye', - avatar: 'https://placekitten.com/50/50?image=77', - }, - { - id: 'user_78', - username: 'Gavin', - avatar: 'https://placekitten.com/50/50?image=78', - }, - { - id: 'user_79', - username: 'Holly', - avatar: 'https://placekitten.com/50/50?image=79', - }, - { - id: 'user_80', - username: 'Isaac', - avatar: 'https://placekitten.com/50/50?image=80', - }, - { - id: 'user_81', - username: 'Julia', - avatar: 'https://placekitten.com/50/50?image=81', - }, - { - id: 'user_82', - username: 'Kevin', - avatar: 'https://placekitten.com/50/50?image=82', - }, - { - id: 'user_83', - username: 'Laura', - avatar: 'https://placekitten.com/50/50?image=83', - }, - { - id: 'user_84', - username: 'Mike', - avatar: 'https://placekitten.com/50/50?image=84', - }, - { - id: 'user_85', - username: 'Nina', - avatar: 'https://placekitten.com/50/50?image=85', - }, - { - id: 'user_86', - username: 'Oscar', - avatar: 'https://placekitten.com/50/50?image=86', - }, - { - id: 'user_87', - username: 'Pam', - avatar: 'https://placekitten.com/50/50?image=87', - }, - { - id: 'user_88', - username: 'Quincy', - avatar: 'https://placekitten.com/50/50?image=88', - }, - { - id: 'user_89', - username: 'Rose', - avatar: 'https://placekitten.com/50/50?image=89', - }, - { - id: 'user_90', - username: 'Sam', - avatar: 'https://placekitten.com/50/50?image=90', - }, - { - id: 'user_91', - username: 'Tara', - avatar: 'https://placekitten.com/50/50?image=91', - }, - { - id: 'user_92', - username: 'Uma', - avatar: 'https://placekitten.com/50/50?image=92', - }, - { - id: 'user_93', - username: 'Victor', - avatar: 'https://placekitten.com/50/50?image=93', - }, - { - id: 'user_94', - username: 'Wendy', - avatar: 'https://placekitten.com/50/50?image=94', - }, - { - id: 'user_95', - username: 'Xander', - avatar: 'https://placekitten.com/50/50?image=95', - }, - { - id: 'user_96', - username: 'Yara', - avatar: 'https://placekitten.com/50/50?image=96', - }, - { - id: 'user_97', - username: 'Zeke', - avatar: 'https://placekitten.com/50/50?image=97', - }, - { - id: 'user_98', - username: 'Ava', - avatar: 'https://placekitten.com/50/50?image=98', - }, - { - id: 'user_99', - username: 'Blake', - avatar: 'https://placekitten.com/50/50?image=99', - }, - { - id: 'user_100', - username: 'Chloe', - avatar: 'https://placekitten.com/50/50?image=100', - }, - ], -}; const tabs = [ { display_name: 'In Discord', id: 'in_discord' }, @@ -531,10 +24,13 @@ let showUser = 0; // usersData[activeTab] = await getUsers(activeTab); -const fetchUsers = async (tabId, page = 1) => { - if (isLoading) return; +export const fetchUsers = async (tabId, page = 1) => { + if (isLoading) { + return; + } isLoading = true; + try { const start = (page - 1) * INITIAL_USERS; const end = start + INITIAL_USERS; @@ -555,7 +51,7 @@ const fetchUsers = async (tabId, page = 1) => { console.log(usersData[tabId]); } currentPage = page; - rerender(App(), document.getElementById('root')); // Re-render the app with the new users + rerender(App(), document.getElementById('root')); } else { console.log('No more users to fetch'); } @@ -566,18 +62,6 @@ const fetchUsers = async (tabId, page = 1) => { } }; -// const handleScroll = () => { -// const scrollPosition = window.innerHeight + window.scrollY; -// const bottomPosition = document.body.offsetHeight - 100; // Trigger fetch 100px from bottom - -// if (scrollPosition >= bottomPosition) { -// // Fetch more users when the user is near the bottom -// fetchUsers(activeTab, currentPage + 1); -// } -// }; - -// window.addEventListener('scroll', handleScroll); - const handleTabNavigation = async (e) => { const selectedTabId = e.target.getAttribute('data_key'); if (selectedTabId) { @@ -620,6 +104,7 @@ export const App = () => { fetchUsers, activeTab, currentPage, + isLoading, }), UserDetailsSection({ user: users[showUser] ?? {} }), ]); diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index 8812d193..46cfc404 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -7,6 +7,7 @@ export const UsersSection = ({ fetchUsers, activeTab, currentPage, + isLoading, }) => { const debounce = (func, delay) => { let timeoutId; @@ -23,12 +24,17 @@ export const UsersSection = ({ debounce(() => { console.log('scroll triggered'); if (window.innerHeight + window.scrollY >= document.body.offsetHeight) { - fetchUsers(activeTab, currentPage + 1); // Fetch next page + fetchUsers(activeTab, currentPage + 1); } }, 200), ); - // handle scroll is not working - add event listener on every scroll element + if (isLoading) { + return createElement('aside', { class: 'users_section' }, [ + createElement('div', { class: 'loading' }, ['Loading...']), + ]); + } + return createElement( 'aside', { diff --git a/users/discord/utils/util.js b/users/discord/utils/util.js index 83cd40e5..6124faea 100644 --- a/users/discord/utils/util.js +++ b/users/discord/utils/util.js @@ -19,3 +19,511 @@ export const getUsers = async (tab) => { console.error(err); } }; +// mock user data +export const mockUsersData = { + in_discord: [ + { + id: 'user_1', + discordId: '123456789', + username: 'Alice', + avatar: 'https://placekitten.com/50/50?image=1', + }, + { + id: 'user_2', + username: 'Bob', + avatar: 'https://placekitten.com/50/50?image=2', + }, + { + id: 'user_3', + username: 'Charlie', + avatar: 'https://placekitten.com/50/50?image=3', + }, + { + id: 'user_4', + username: 'David', + avatar: 'https://placekitten.com/50/50?image=4', + }, + { + id: 'user_5', + username: 'Eve', + avatar: 'https://placekitten.com/50/50?image=5', + }, + { + id: 'user_6', + username: 'Fay', + avatar: 'https://placekitten.com/50/50?image=6', + }, + { + id: 'user_7', + username: 'George', + avatar: 'https://placekitten.com/50/50?image=7', + }, + { + id: 'user_8', + username: 'Hannah', + avatar: 'https://placekitten.com/50/50?image=8', + }, + { + id: 'user_9', + username: 'Isaac', + avatar: 'https://placekitten.com/50/50?image=9', + }, + { + id: 'user_10', + username: 'Jill', + avatar: 'https://placekitten.com/50/50?image=10', + }, + { + id: 'user_11', + username: 'Karl', + avatar: 'https://placekitten.com/50/50?image=11', + }, + { + id: 'user_12', + username: 'Lily', + avatar: 'https://placekitten.com/50/50?image=12', + }, + { + id: 'user_13', + username: 'Max', + avatar: 'https://placekitten.com/50/50?image=13', + }, + { + id: 'user_14', + username: 'Nina', + avatar: 'https://placekitten.com/50/50?image=14', + }, + { + id: 'user_15', + username: 'Oscar', + avatar: 'https://placekitten.com/50/50?image=15', + }, + { + id: 'user_16', + username: 'Pam', + avatar: 'https://placekitten.com/50/50?image=16', + }, + { + id: 'user_17', + username: 'Quinn', + avatar: 'https://placekitten.com/50/50?image=17', + }, + { + id: 'user_18', + username: 'Rachel', + avatar: 'https://placekitten.com/50/50?image=18', + }, + { + id: 'user_19', + username: 'Sam', + avatar: 'https://placekitten.com/50/50?image=19', + }, + { + id: 'user_20', + username: 'Tina', + avatar: 'https://placekitten.com/50/50?image=20', + }, + { + id: 'user_21', + username: 'Uma', + avatar: 'https://placekitten.com/50/50?image=21', + }, + { + id: 'user_22', + username: 'Victor', + avatar: 'https://placekitten.com/50/50?image=22', + }, + { + id: 'user_23', + username: 'Wendy', + avatar: 'https://placekitten.com/50/50?image=23', + }, + { + id: 'user_24', + username: 'Xander', + avatar: 'https://placekitten.com/50/50?image=24', + }, + { + id: 'user_25', + username: 'Yvonne', + avatar: 'https://placekitten.com/50/50?image=25', + }, + { + id: 'user_26', + username: 'Zack', + avatar: 'https://placekitten.com/50/50?image=26', + }, + { + id: 'user_27', + username: 'Aaron', + avatar: 'https://placekitten.com/50/50?image=27', + }, + { + id: 'user_28', + username: 'Bianca', + avatar: 'https://placekitten.com/50/50?image=28', + }, + { + id: 'user_29', + username: 'Carlos', + avatar: 'https://placekitten.com/50/50?image=29', + }, + { + id: 'user_30', + username: 'Diana', + avatar: 'https://placekitten.com/50/50?image=30', + }, + { + id: 'user_31', + username: 'Eli', + avatar: 'https://placekitten.com/50/50?image=31', + }, + { + id: 'user_32', + username: 'Fiona', + avatar: 'https://placekitten.com/50/50?image=32', + }, + { + id: 'user_33', + username: 'Gus', + avatar: 'https://placekitten.com/50/50?image=33', + }, + { + id: 'user_34', + username: 'Holly', + avatar: 'https://placekitten.com/50/50?image=34', + }, + { + id: 'user_35', + username: 'Ian', + avatar: 'https://placekitten.com/50/50?image=35', + }, + { + id: 'user_36', + username: 'Julia', + avatar: 'https://placekitten.com/50/50?image=36', + }, + { + id: 'user_37', + username: 'Kevin', + avatar: 'https://placekitten.com/50/50?image=37', + }, + { + id: 'user_38', + username: 'Laura', + avatar: 'https://placekitten.com/50/50?image=38', + }, + { + id: 'user_39', + username: 'Mike', + avatar: 'https://placekitten.com/50/50?image=39', + }, + { + id: 'user_40', + username: 'Nora', + avatar: 'https://placekitten.com/50/50?image=40', + }, + { + id: 'user_41', + username: 'Oliver', + avatar: 'https://placekitten.com/50/50?image=41', + }, + { + id: 'user_42', + username: 'Paula', + avatar: 'https://placekitten.com/50/50?image=42', + }, + { + id: 'user_43', + username: 'Quincy', + avatar: 'https://placekitten.com/50/50?image=43', + }, + { + id: 'user_44', + username: 'Rose', + avatar: 'https://placekitten.com/50/50?image=44', + }, + { + id: 'user_45', + username: 'Steve', + avatar: 'https://placekitten.com/50/50?image=45', + }, + { + id: 'user_46', + username: 'Tara', + avatar: 'https://placekitten.com/50/50?image=46', + }, + { + id: 'user_47', + username: 'Ulysses', + avatar: 'https://placekitten.com/50/50?image=47', + }, + { + id: 'user_48', + username: 'Violet', + avatar: 'https://placekitten.com/50/50?image=48', + }, + { + id: 'user_49', + username: 'Wes', + avatar: 'https://placekitten.com/50/50?image=49', + }, + { + id: 'user_50', + username: 'Xena', + avatar: 'https://placekitten.com/50/50?image=50', + }, + ], + verified: [ + { + id: 'user_51', + username: 'Frank', + avatar: 'https://placekitten.com/50/50?image=51', + }, + { + id: 'user_52', + username: 'Grace', + avatar: 'https://placekitten.com/50/50?image=52', + }, + { + id: 'user_53', + username: 'Henry', + avatar: 'https://placekitten.com/50/50?image=53', + }, + { + id: 'user_54', + username: 'Ivy', + avatar: 'https://placekitten.com/50/50?image=54', + }, + { + id: 'user_55', + username: 'Jack', + avatar: 'https://placekitten.com/50/50?image=55', + }, + { + id: 'user_56', + username: 'Kim', + avatar: 'https://placekitten.com/50/50?image=56', + }, + { + id: 'user_57', + username: 'Leo', + avatar: 'https://placekitten.com/50/50?image=57', + }, + { + id: 'user_58', + username: 'Mila', + avatar: 'https://placekitten.com/50/50?image=58', + }, + { + id: 'user_59', + username: 'Nate', + avatar: 'https://placekitten.com/50/50?image=59', + }, + { + id: 'user_60', + username: 'Olivia', + avatar: 'https://placekitten.com/50/50?image=60', + }, + { + id: 'user_61', + username: 'Paul', + avatar: 'https://placekitten.com/50/50?image=61', + }, + { + id: 'user_62', + username: 'Quinn', + avatar: 'https://placekitten.com/50/50?image=62', + }, + { + id: 'user_63', + username: 'Ruby', + avatar: 'https://placekitten.com/50/50?image=63', + }, + { + id: 'user_64', + username: 'Steve', + avatar: 'https://placekitten.com/50/50?image=64', + }, + { + id: 'user_65', + username: 'Tina', + avatar: 'https://placekitten.com/50/50?image=65', + }, + { + id: 'user_66', + username: 'Ulysses', + avatar: 'https://placekitten.com/50/50?image=66', + }, + { + id: 'user_67', + username: 'Vera', + avatar: 'https://placekitten.com/50/50?image=67', + }, + { + id: 'user_68', + username: 'Walter', + avatar: 'https://placekitten.com/50/50?image=68', + }, + { + id: 'user_69', + username: 'Xena', + avatar: 'https://placekitten.com/50/50?image=69', + }, + { + id: 'user_70', + username: 'Yvonne', + avatar: 'https://placekitten.com/50/50?image=70', + }, + { + id: 'user_71', + username: 'Zane', + avatar: 'https://placekitten.com/50/50?image=71', + }, + { + id: 'user_72', + username: 'Alan', + avatar: 'https://placekitten.com/50/50?image=72', + }, + { + id: 'user_73', + username: 'Bella', + avatar: 'https://placekitten.com/50/50?image=73', + }, + { + id: 'user_74', + username: 'Chris', + avatar: 'https://placekitten.com/50/50?image=74', + }, + { + id: 'user_75', + username: 'Daisy', + avatar: 'https://placekitten.com/50/50?image=75', + }, + { + id: 'user_76', + username: 'Ethan', + avatar: 'https://placekitten.com/50/50?image=76', + }, + { + id: 'user_77', + username: 'Faye', + avatar: 'https://placekitten.com/50/50?image=77', + }, + { + id: 'user_78', + username: 'Gavin', + avatar: 'https://placekitten.com/50/50?image=78', + }, + { + id: 'user_79', + username: 'Holly', + avatar: 'https://placekitten.com/50/50?image=79', + }, + { + id: 'user_80', + username: 'Isaac', + avatar: 'https://placekitten.com/50/50?image=80', + }, + { + id: 'user_81', + username: 'Julia', + avatar: 'https://placekitten.com/50/50?image=81', + }, + { + id: 'user_82', + username: 'Kevin', + avatar: 'https://placekitten.com/50/50?image=82', + }, + { + id: 'user_83', + username: 'Laura', + avatar: 'https://placekitten.com/50/50?image=83', + }, + { + id: 'user_84', + username: 'Mike', + avatar: 'https://placekitten.com/50/50?image=84', + }, + { + id: 'user_85', + username: 'Nina', + avatar: 'https://placekitten.com/50/50?image=85', + }, + { + id: 'user_86', + username: 'Oscar', + avatar: 'https://placekitten.com/50/50?image=86', + }, + { + id: 'user_87', + username: 'Pam', + avatar: 'https://placekitten.com/50/50?image=87', + }, + { + id: 'user_88', + username: 'Quincy', + avatar: 'https://placekitten.com/50/50?image=88', + }, + { + id: 'user_89', + username: 'Rose', + avatar: 'https://placekitten.com/50/50?image=89', + }, + { + id: 'user_90', + username: 'Sam', + avatar: 'https://placekitten.com/50/50?image=90', + }, + { + id: 'user_91', + username: 'Tara', + avatar: 'https://placekitten.com/50/50?image=91', + }, + { + id: 'user_92', + username: 'Uma', + avatar: 'https://placekitten.com/50/50?image=92', + }, + { + id: 'user_93', + username: 'Victor', + avatar: 'https://placekitten.com/50/50?image=93', + }, + { + id: 'user_94', + username: 'Wendy', + avatar: 'https://placekitten.com/50/50?image=94', + }, + { + id: 'user_95', + username: 'Xander', + avatar: 'https://placekitten.com/50/50?image=95', + }, + { + id: 'user_96', + username: 'Yara', + avatar: 'https://placekitten.com/50/50?image=96', + }, + { + id: 'user_97', + username: 'Zeke', + avatar: 'https://placekitten.com/50/50?image=97', + }, + { + id: 'user_98', + username: 'Ava', + avatar: 'https://placekitten.com/50/50?image=98', + }, + { + id: 'user_99', + username: 'Blake', + avatar: 'https://placekitten.com/50/50?image=99', + }, + { + id: 'user_100', + username: 'Chloe', + avatar: 'https://placekitten.com/50/50?image=100', + }, + ], +}; From 31a8a1b3a3476685fbdea454aea99af5f8fcd10b Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Tue, 15 Oct 2024 19:59:06 +0530 Subject: [PATCH 13/15] fixed loading psinner issue --- users/discord/App.js | 6 +----- users/discord/components/UsersSection.js | 1 - 2 files changed, 1 insertion(+), 6 deletions(-) diff --git a/users/discord/App.js b/users/discord/App.js index 73aeda96..ae98bd1e 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -40,25 +40,21 @@ export const fetchUsers = async (tabId, page = 1) => { if (newUsers.length > 0) { if (page === 1) { usersData[tabId] = newUsers; // Initial load - console.log('Fetched initial users'); } else { const existingIds = new Set(usersData[tabId].map((user) => user.id)); const uniqueNewUsers = newUsers.filter( (user) => !existingIds.has(user.id), ); usersData[tabId] = [...usersData[tabId], ...uniqueNewUsers]; - console.log('Fetched more users'); - console.log(usersData[tabId]); } currentPage = page; - rerender(App(), document.getElementById('root')); } else { - console.log('No more users to fetch'); } } catch (error) { console.error('Error fetching users', error); } finally { isLoading = false; + rerender(App(), document.getElementById('root')); } }; diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index 46cfc404..28617444 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -22,7 +22,6 @@ export const UsersSection = ({ window.addEventListener( 'scroll', debounce(() => { - console.log('scroll triggered'); if (window.innerHeight + window.scrollY >= document.body.offsetHeight) { fetchUsers(activeTab, currentPage + 1); } From b3c7664c3c5500f37b540357022bcdb64a321d99 Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Wed, 16 Oct 2024 21:11:54 +0530 Subject: [PATCH 14/15] removed empty else block --- users/discord/App.js | 1 - 1 file changed, 1 deletion(-) diff --git a/users/discord/App.js b/users/discord/App.js index ae98bd1e..5bbb1858 100644 --- a/users/discord/App.js +++ b/users/discord/App.js @@ -48,7 +48,6 @@ export const fetchUsers = async (tabId, page = 1) => { usersData[tabId] = [...usersData[tabId], ...uniqueNewUsers]; } currentPage = page; - } else { } } catch (error) { console.error('Error fetching users', error); From 2155129b87717191df9c2ed02549b8f1b498723c Mon Sep 17 00:00:00 2001 From: Ishan Veer Date: Thu, 17 Oct 2024 18:56:34 +0530 Subject: [PATCH 15/15] removed debounce function as it is already defined globally --- users/discord/components/UsersSection.js | 11 +---------- 1 file changed, 1 insertion(+), 10 deletions(-) diff --git a/users/discord/components/UsersSection.js b/users/discord/components/UsersSection.js index 28617444..a4e569ec 100644 --- a/users/discord/components/UsersSection.js +++ b/users/discord/components/UsersSection.js @@ -9,19 +9,10 @@ export const UsersSection = ({ currentPage, isLoading, }) => { - const debounce = (func, delay) => { - let timeoutId; - return function (...args) { - clearTimeout(timeoutId); - timeoutId = setTimeout(() => { - func.apply(this, args); - }, delay); - }; - }; - window.addEventListener( 'scroll', debounce(() => { + console.log('scroll triggered'); if (window.innerHeight + window.scrollY >= document.body.offsetHeight) { fetchUsers(activeTab, currentPage + 1); }