Created
October 19, 2023 12:20
-
-
Save anartzdev/13498ed353f6c05ba5e1e7d8ac1cdb80 to your computer and use it in GitHub Desktop.
Componente Data Fetching Rest
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#alert-year-input { | |
background: #f5f5b0; | |
border: 2.5px solid #b0b083; | |
padding: 1rem; | |
margin: 10px; | |
border-radius: 1rem; | |
color: #68683e; | |
} | |
#alert-year-input:hover { | |
cursor: pointer; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { | |
component$, | |
useStore, | |
Resource, | |
useResource$, | |
$, | |
useSignal, | |
useStyles$, | |
} from '@builder.io/qwik'; | |
import styles from './index.css?inline' | |
export const DataFetchingRest = component$(() => { | |
useStyles$(styles); | |
const currentYear = new Date().getFullYear(); | |
const incorrectYear = useSignal(false); | |
const store = useStore({ | |
year: currentYear, | |
races: [], | |
}); | |
const API_URL = 'https://ergast.com/api/f1/'; | |
// https://ergast.com/api/f1/<AÑO>.json | |
const getF1RacesByYear = $( | |
async (year: number, controller?: AbortController): Promise<Array<any>> => { | |
const endPoint = `${year}.json`; | |
if (year < 1950 || year > currentYear) { | |
controller?.abort('incorrect year'); | |
incorrectYear.value = true; | |
store.year = currentYear; | |
} | |
const url = `${API_URL}${endPoint}`; | |
const data = await fetch(url, { | |
method: 'GET', | |
signal: controller?.signal, | |
}); | |
const json: Array<any> = (await data.json())['MRData']['RaceTable'][ | |
'Races' | |
]; | |
return Array.isArray(json) ? json : [Promise.reject(json)]; | |
} | |
); | |
const f1RacesResource = useResource$<any>(({ track, cleanup }) => { | |
// Usamos `track` para realizar nuevas consultas cuando cambia el año | |
track(() => store.year); | |
// La función `cleanup` se ejecuta cuando se está re-ejecutando y | |
// el controlador `AbortController` puede abortar la operación anterior porque s ha interrumpido. | |
const abortController = new AbortController(); | |
cleanup(() => abortController.abort()); | |
// Se obtiene el lista de carreras con el año seleccionado. | |
return getF1RacesByYear(store.year, abortController); | |
}); | |
return ( | |
<div> | |
{incorrectYear.value && ( | |
<div id='alert-year-input' onClick$={() => (incorrectYear.value = false)}> | |
El año introducido debe de ser 1950 (incluido) hasta el año actual | |
(incluido) que es {currentYear}. Se asigna el actual por defecto | |
</div> | |
)} | |
<div> | |
<input | |
type='text' | |
value={store.year} | |
maxLength={4} | |
placeholder='Añadir año entre 1950 y el actual (incluidos) para lista de carreras' | |
onInput$={(ev) => { | |
setTimeout(() => { | |
store.year = +(ev.target as HTMLInputElement).value; | |
}, 1000); | |
}} | |
class='text-l w-96 max-w-full rounded border-0 bg-white px-4 py-4 shadow outline-none placeholder:italic focus:outline-none focus:ring' | |
/> | |
</div> | |
<div id='data'> | |
<Resource | |
value={f1RacesResource} | |
onPending={() => ( | |
<div class='grow animate-pulse rounded-md bg-gray-200 text-left'> | |
Loading... | |
</div> | |
)} | |
onRejected={(error) => ( | |
<div | |
class='grow rounded border border-solid border-red-300 bg-red-100 p-4 text-center text-red-500' | |
role='error-message' | |
> | |
Error: {error.message} | |
</div> | |
)} | |
onResolved={(result) => ( | |
<> | |
<div class='mr-4 season-data'> | |
Current Year: {result && result[0].season} | |
</div> | |
<div class='text-left' role='display-message'> | |
<ul> | |
{result && | |
result.map((race: any) => { | |
return ( | |
<li | |
class='race-item' | |
key={`race_${store.year}_${race.round}`} | |
> | |
{race.round} - {race.raceName} | |
</li> | |
); | |
})} | |
</ul> | |
</div> | |
</> | |
)} | |
/> | |
</div> | |
</div> | |
); | |
}); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment