Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import React, { useEffect, useState } from 'react';
- import './App.css';
- const headers = [
- { key: 'firstName', value: 'First Name' },
- { key: 'lastName', value: 'Last Name' },
- { key: 'street', value: 'Street Address' },
- { key: 'city', value: 'City' },
- { key: 'state', value: 'State' },
- { key: 'country', value: 'Country' },
- { key: 'postcode', value: 'Postal Code' },
- { key: 'latitude', value: 'Latitude' },
- { key: 'longitude', value: 'Longitude' }
- ]
- function App() {
- const [isLoading, setIsLoading] = useState(true)
- const [errorLoading, setErrorLoading] = useState(false)
- const [data, setData] = useState<any[]>([])
- const [sortedData, setSortedData] = useState<any[]>([])
- const [sorting, setSorting] = useState(0)
- const [searchValue, setSearchValue] = useState('')
- useEffect(() => {
- fetch('https://randomuser.me/api/?results=20')
- .then((response) => response.json())
- .then((data) => data.results)
- .then((data: any[]) => {
- const filtered: any[] = data.map((obj) => {
- const { street, coordinates, timezone, ...rest } = obj.location
- return ({
- firstName: obj.name.first,
- lastName: obj.name.last,
- street: `${street.number} ${street.name}`,
- latitude: coordinates.latitude,
- longitude: coordinates.longitude,
- ...rest
- })
- })
- setData(filtered)
- setSortedData(filtered)
- setIsLoading(false)
- })
- .catch((err) => {
- setIsLoading(false)
- setErrorLoading(true)
- console.error(err)
- })
- }, [])
- // Sets the sortedData anytime sorting or searchValue change
- useEffect(() => {
- const index = Math.abs(sorting) - 1
- let newData = [...data]
- if (index >= 0) {
- const key = headers[index].key
- newData = newData.sort((a, b) => a[key] === b[key] ? 0 : a[key] > b[key] ? 1 : -1)
- if (sorting < 0) newData.reverse()
- }
- setSortedData(newData.filter((value) => {
- return Object.values(value).some((element) => `${element}`.toLowerCase().includes(searchValue.toLowerCase()))
- }))
- // eslint-disable-next-line
- }, [sorting, searchValue])
- if (isLoading)
- return <div className="App">Loading...</div>
- if (errorLoading)
- return <div className="App">Error: Could not fetch data!</div>
- return (
- <div className="App">
- <input value={searchValue} onChange={(e) => {
- setSearchValue(e.target.value)
- }} />
- <table>
- <thead>
- <tr>
- {headers.map((header, headerIdx) => (
- <th
- style={{ userSelect: 'none', cursor: 'pointer' }}
- key={headerIdx}
- onClick={() => {
- setSorting(sorting < 0 ? 0 : (sorting >= 0 && ++headerIdx !== sorting) ? headerIdx : -headerIdx)
- }}
- >{header.value}</th>
- ))}
- </tr>
- </thead>
- <tbody>
- {sortedData.map((data, dataIdx) => (
- <tr key={dataIdx}>
- {headers.map((header, headerIdx) => <td key={headerIdx}>{data[header.key]}</td>)}
- </tr>
- ))}
- </tbody>
- </table>
- </div>
- );
- }
- export default App;
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement