No tienes acceso a esta clase

隆Contin煤a aprendiendo! 脷nete y comienza a potenciar tu carrera

Consumiendo API

21/26
Recursos

Aportes 49

Preguntas 24

Ordenar por:

驴Quieres ver m谩s aportes, preguntas y respuestas de la comunidad?

隆Hola t煤! Si como yo, quer铆as aplicar la API para otro canal de YouTube (Lo siento profe, quer铆a probar con otros canales, no tengo nada en contra del tuyo), pueden averiguar el ID del can谩l con el siguiente link:
https://commentpicker.com/youtube-channel-id.php
Introducen la URL del can谩l de YouTube, para este ejemplo tom茅 el canal de EnchufeTv cuya URL es la siguiente en YouTube:
https://www.youtube.com/c/enchufetv
Y el resultado de esta p谩gina fue el siguiente:
UCoGDh1Xa3kUCpok24JN5DKA
Dejando el ID en rapidapi.

Espero que sea de ayuda.

馃搥 饾棖饾椆饾棶饾榾饾棽 #饾煭饾煷: 饾棖饾椉饾椈饾榾饾槀饾椇饾椂饾棽饾椈饾棻饾椉 饾棓饾棧饾棞 饾煭饾煷/饾煯饾煭 馃搥
.
馃敡 Continuando con la l贸gica de la landing:
.

  • Entra a https://rapidapi.com/ y creamos una cuenta al dar click en Sign Up y seguir los pasos.
  • El profesor usar谩 la API de youtube, as铆 que en el buscador puedes colocar la API que quieras usar. La versi贸n de la API de youtube que vamos a usar es YouTube V3.
  • Una vez seleccionada la API, nos mostrar谩 3 columnas con los servicios y herramientas que est谩n disponibles para la API, para el ejemplo se selecciona Channel Videos para obtener los 煤ltimos v铆deos publicados. En la columna central, se debe indicar la id del canal que queremos mostrar en la landing, 茅ste se obtiene en la url de youtube despu茅s de channel/, por ejemplo para el canal de youtube del profesor: https://www.youtube.com/channel/UC9k0tTsh_qStx0HPuPftSsg el id del canal es UC9k0tTsh_qStx0HPuPftSsg ese es el que se debe pegar en el par谩metro channeld.
  • M谩s abajo, se puede configurar el m谩ximo de v铆deos que se desea obtener (m谩ximo hasta 50), para el ejemplo se coloc贸 9.
  • En la tercera columna, se selecciona en la lista el lenguaje de programaci贸n y el m茅todo que se quiere usar, en este caso: JavaScript 鈫 fetch con 茅sto aparecer谩 la plantilla del c贸digo.
  • Para visualizar la salida al testear la plantilla, en la columna del medio al dar click en Test Endpoint, la pesta帽a Results se activa y podemos conocer cada uno de los elementos de los objetos, esa informaci贸n nos ser谩 煤til para nuestro el c贸digo.
  • Copiar la plantilla e ir al editor VSC en la ruta src/assets y pegarlo en main.js
  • La url que se pasa por argumento a la funci贸n fetch, la cambiamos al inicio del c贸digo para declarar la constante API:
const API = 'https://youtube-v31.p.rapidapi.com/search?channelId=UCw05fUBPwmpu-ehXFMqfdMw&part=snippet%2Cid&order=date&maxResults=9';

La variable options si la dejamos igual, tal cual como lo muestra rapidapi:

const options = {
    method: 'GET',
    headers: {
        'X-RapidAPI-Key': '6540473ff4mshfbdbb244ab22f99p10c708jsnfd294791e746',
		'X-RapidAPI-Host': 'youtube-v31.p.rapidapi.com'
    }
};

Como vamos a usar el asyn/await, borramos el c贸digo de fetch estructurado con then y catch. En lugar de ello, usamos la l贸gica que hicimos en ejemplos anteriores:

//L贸gica de async: ir por los datos, luego esperar por ellos y finalmente retornarlos hacia el usuario
async function fetchData(urlApi) { //siempre async antes de function
const response = await fetch(urlApi, options); //hacemos uso del fetch() y solo por esta vez le pasamos la opciones 
const data = await response.json(); //estructura de los datos transformandolos en json
return data; //retorna la informaci贸n de la API que estamos solicitando
}

Ahora vamos usar un nuevo concepto: una funci贸n que se invoca a s铆 misma; con JavaScript podemos tener funciones an贸nimas que permitan llamarse autom谩ticamente, la estructura cuenta con la palabra reservada **async **y con funciones arrows:

(async () => {
//Dentro implementamos la l贸gica necesaria para hacer el llamado a la API, obtener los elementos y mostrarlos en html
//Se implementa try y catch
try{
} catch {
}
})();

Dentro de try{} estar谩 el llamado de la API y el template de html para interpretar los datos a iterar por cada objeto, en este caso, cuando analizamos la salida de la API en rapidapi, hay una jerarqu铆a de los datos, est谩n los 9 鈥渋tems鈥 del 0 al 8 para la posici贸n de cada v铆deo, luego el 鈥渟nippet鈥 de cada item, luego 鈥渢humbnails鈥 y 茅ste a su vez los tama帽os de la imagen (nos interesa con la m谩s alta resoluci贸n 鈥渉igh鈥), tambi茅n nos interesa mostrar la descripci贸n 鈥渄escription鈥 y nombre 鈥渢itle鈥 de cada v铆deo:

(async () => {
    try {
        const videos = await fetchData(API);
        let view = `
        ${videos.items.map(video => `
            <div class="group relative">
                <div
                    class="w-full bg-gray-200 aspect-w-1 aspect-h-1 rounded-md overflow-hidden group-hover:opacity-75 lg:aspect-none">
                    <img src="${video.snippet.thumbnails.high.url}" alt="${video.snippet.description}" class="w-full">
                </div>
                <div class="mt-4 flex justify-between">
                    <h3 class="text-sm text-gray-700" style="color:white;">
                        <span aria-hidden="true" class="absolute inset-0"></span>
                        ${video.snippet.title}
                    </h3>
                </div>
            </div>
        `).slice(0, 4).join('')}
        `;
        content.innerHTML = view;
    } catch {
     
    }
})();
  • Si quieres saber m谩s del m茅todo map, en el enlace hay ejemplos: aqu铆
    • Para el m茅todo slice: aqu铆
    • Para el m茅todo join: aqu铆
  • En index.html buscamos el comentario de <!-- content --> para agregar el id de **++content ++**y pueda mostrar los v铆deos en la landing, para ello, borramos el div despu茅s del comentario, incluyendo su contenido, queda as铆:
<div class="mt-6 grid grid-cols-1 gap-y-10 gap-x-6 sm:grid-cols-2 lg:grid-cols-4 xl:gap-x-8" id="content">
<!-- content -->
</div>

Y ahora para que pueda leer la l贸gica de main, dado que el id lo llamamos content, en el archivo main agregamos la referencia content:

const content = null || document.getElementById('content');

puede que haya mejorado este curso a comparacion con el anterior pero lo tienen que volver a hacer una tercera vez, en espa帽ol

ya no sale el Id del canal en la url si quieren encontrarlo abran el canal que quieren la lista

le dan ctrl + u para que te muestre el codigo de fuente
luego ctrl + f para buscar un text

y en el cuadro para buscar pegan https://www.youtube.com/channel/

ahi te va a salir una url con el id asi
https://www.youtube.com/channel/[aca_va_el_id]

Si no tienes imagen para colocar en el hero pueden usar este enlace https://picsum.photos/500 les dar谩 una imagen distinta cada vez que recarguen la p谩gina

Una buena sugerencia para platzi es que los cursos siempre piensen que estan hablando a gente que no sabe nada, en particular hago muchos cursos y leo y me documento pero a veces no entiendo lo que el profe explica y hay algunos profes que se me dificulta coger la linea de lo que hacen.
El curso de API REST con express fue super bueno, el profesor alli me aclaro muchisimos vacios que creo que tenia, este curso en particular tambien ha sido muy bueno pero hay momentos donde se pierde uno con el profe, es un punto por mejorar porque con el profe oscar en los cursos que he iniciado me ha pasado. He notado que el profe tiene que leer mucho algun telepronter, tal vez sea eso, cuando uno ense帽a algo que domina y mas conversadito fluye mejor.

funciones anonimas autoejecutables!!!

Les recomiendo hacer una copia del resultado de la API, pues al final si les pasa alg煤n error o si est谩n haciendo mejoras les va a sacar un status of 429 (Too Many Requests). Esto es porque la API tiene un l铆mite de 40 peticiones MENSUALES,

solo quiero terminar este curso para buscar otro que me explique mejor.

Este es el ID de el profesor Oscar ( UC9k0tTsh_qStx0HPuPftSsg )

Aqu铆 esta la API que utiliza el profesor en este video: Youtube V3

Para los que igual que un servidor solo tienen un idea no muy clara sobre lo que es una api. Aqu铆 unos links que les puede ayudar a tender mejor.
link1
link2

Este es el codigo de HTML que hace falta en el minuto 13:20

<div class="group relative">
            <div
              class="w-full bg-gray-200 aspect-w-1 aspect-h-1 rouded-md overflow-hidden group-hover:opacity-75 lg:aspect-none"
            >
              <img src="" alt="" class="w-full" />
            </div>
            <div class="mt-4 flex justify-between">
              <h3 class="text-sm text-gray-700">
                <span aria-hidden="true" class="absolute inset-0"></span>
                Title
              </h3>
            </div>
          </div>

馃檵鈥嶁檪锔 Quiero compartir un link donde resume:

de manera 馃憠 simple y concreta 馃憟
.

spoiler. Minuto 11:43 ** 隆funciones anonimas autoejecutables!** hagame el鈥 favor. Se dieron garra. Bien por el profe y su dominio del tema, mal por que los conceptos se asumen que ya 鈥渟e saben鈥
.
Este curso desentona de todos los que he tomado. Mucho tecnisismo y teoria nunca antes vista

Esta plataforma de RapidApi es increible!

Decidi construir mi propia API para poner en practica mis habilidades de backend y tener un portafolio mas completo. Me va a tocar hcaer mucho trabajo 馃槖 pero aqui pueden ir viendo el progreso de este proyecto.

Decidi hacer un blog financiero (estudio finanzas en la universidad) que incluya un blog, seccion de noticias, calculadoras y una seccion de contacto. Deseenme suerte.

https://github.com/EsquizoDEV/financeBlog

Tambien ire comentando por aqui algunos avances:

Dejo el primer avance, super importante primero ir definiendo que queremos que haga nuestra aplicacion, antes de pasar a programar como locos, entonces es lo que estoy haciendo.

La p谩gina tendr谩 3 secciones principales, un blog, noticias, una secci贸n de calculadoras y una secci贸n de contacto.
El blog, consumir谩 el contenido principal (texto e im谩genes) desde una API construida en NodeJS, express y utilizando una base de datos SQL, esto nos permitir谩 crear una misma estructura para el frontend del blog y simplemente consumir los datos sin perder el estilo.
Para el blog la API tendr谩 varios niveles, un nivel para obtener informaci贸n de todos los blogs actuales, que ser谩n utilizados para mostrarse en un carrusel, el API debe responder con informaci贸n general de cada blog (Blog Nivel 0 Especificacion).
Tambi茅n habr谩 un nivel para obtener a el detalle de un blog, la estructura de respuesta de este request, tiene que ser la correcta para el renderizado adecuado del frontend. En el frontend, nuestro Javascript, necesita saber la estructura de esa entrada de blog, es decir, necesitamos saber el titulo principal, la introducci贸n, la cantidad de subt铆tulos que hay a lo largo del blog, y los contenidos relativos a cada subtitulo, as铆 tambi茅n, cada secci贸n puede ir o no acompa帽ada de una imagen, que tendr谩 que aparecer entre cada cambio de secci贸n. Para ver mejor un ejemplo de respuesta, ir a la especificaci贸n de Blog Api Nivel 1.
Blog API Nivel 0 especificacion:
Rutas, m茅todos y ejemplos de respuesta:
Ruta: api/ V1/blogs
Method: GET
Res example:
[{
鈥淭itle鈥: 鈥漈he first entry鈥,
鈥淪hortContent鈥:鈥漈he short content string鈥,
鈥淒ate鈥: 27/05/22,
鈥淚d鈥: 鈥123456鈥
}]
Blog API nivel 1 especificaci贸n:
Ruta: api/v1/blog/:id
Method: GET
Res example:
{
鈥淭itle鈥: 鈥淏log title鈥
鈥淢ainIMG鈥: 鈥淚MG SRC鈥,
鈥淚ntro鈥: 鈥淪tring intro鈥,
鈥淪ubContent鈥: [{
鈥淭itle鈥: 鈥淪ubtitle 1鈥,
鈥淐ontent鈥: 鈥淐ontent string鈥,
鈥淚mage鈥: 鈥淚MG SRC鈥
}]
}

Otra forma de averiguar el channel ID es la siguiente: 1\. Ingresas al canal de tu elecci贸n, en mi caso el de la NASA: <https://www.youtube.com/@nasa_es> 2\. Le das click a su descripci贸n (se帽alado con la l铆nea roja): ![](https://static.platzi.com/media/user_upload/image-e65bbfb3-df94-4cad-a3d9-c5a0416d2a0e.jpg)3. Das click en compartir canal: ![](https://static.platzi.com/media/user_upload/image-65109e1b-3510-43e6-983c-2cfb90a94e3e.jpg) 4\. Seleccionas la opci贸n "Copiar ID del Canal" ![](https://static.platzi.com/media/user_upload/image-8dc8ab78-bc7f-4cc7-ad98-4ba7f0fb04bb.jpg) Y listo, 隆celebra! Ya tienes el ID de canal.

Debemos tener en cuenta que en el ambito laboral necesitaremos buscar informacion de manera inmediata si no la recordamos, aprovechemos los vacios de informacion para buscarla nosotros mismos. somos responsables de nuestro aprendizaje , aunque si , la explicacion esta bastante intensa y poco fluida

genial curso

Me encanta esta clase, es un buen m茅todo sin hacer tantos id en el HTML, solo un getElementById y esta todo

const API = 'https://youtube-v31.p.rapidapi.com/search?channelId=UCBVjMGOIkavEAhyqpxJ73Dw&part=snippet%2Cid&order=date&maxResults=9'

const content = null || document.getElementById('content')

const options = {
	method: 'GET',
	headers: {
		'X-RapidAPI-Key': 'd3fb83269emsh45c3e7bb4dff737p1c5116jsn290e84273e9f',
		'X-RapidAPI-Host': 'youtube-v31.p.rapidapi.com'
	}
};

async function fetchData(urlApi){
  const response = await fetch(urlApi, options);
  const data = await response.json();
  return data;
}

(async () =>{
try {
  const videos = await fetchData(API);
  let view = `
  ${videos.items.map(video => `
        <div class="group relative">
          <div
            class="w-full bg-gray-200 aspect-w-1 aspect-h-1 rounded-md overflow-hidden group-hover:opacity-75 lg:aspect-none">
            <img src="${video.snippet.thumbnail.high.url}" alt="${video.snippet.description}" class="w-full">
          </div>
          <div class="mt-4 flex justify-between">
            <h3 class="text-sm text-gray-700">
              <span aria-hidden="true" class="absolute inset-0"></span>
              ${video.snippet.title}
            </h3>
          </div>
        </div>
  `).slice(0,4).join('')}
  
  `;
} catch (error) {
  
}
})();

Esta clase me volo la cabeza. Hice todo lo que dijo el profesor pero no entendi muy bien el porque de todo eso. No se si es mi culpa o es que el curso va muy rapido鈥 pero me hubiese gustado que explicaran detalladamente el porque de cada cosa en lugar de solo ir al grano

ID Platzi Chanel :

UC55-mxUj5Nj3niXFReG44OQ

Para aquellos que est茅n usando TypeScript, les comparto las interfaces para la API. 馃槃

export interface Video {
    kind:          string;
    nextPageToken: string;
    regionCode:    string;
    items:         Item[];
}

export interface Item {
    kind:    string;
    id:      ID;
    snippet: Snippet;
}

export interface ID {
    kind:    string;
    videoId: string;
}

export interface Snippet {
    channelId:            string;
    channelTitle:         string;
    description:          string;
    liveBroadcastContent: string;
    publishTime:          Date;
    publishedAt:          Date;
    title:                string;
    thumbnails:           Thumbnails;
}

export interface Thumbnails {
    default: Default;
    high:    Default;
    medium:  Default;
}

export interface Default {
    height: number;
    url:    string;
    width:  number;
}

Aqui el codigo con una explicacion breve de lo que hizo Oscar

const API = `https://youtube-v31.p.rapidapi.com/search?channelId=UCMebXsaxWdvBzBNwus7TmxA&part=snippet%2Cid&order=date&maxResults=9`;

//aqui agregaremos la iteracion de cada elemento(referencia)
const content = null || document.getElementById('content');

const options = {
	method: 'GET',
	headers: {
		'X-RapidAPI-Key': 'd184c3e23amsh3f130883e71e936p1675cdjsn5a978ab2864a',
		'X-RapidAPI-Host': 'youtube-v31.p.rapidapi.com'
	}
};

async function fetchData(urlApi){
    const response = await fetch(urlApi, options)
    const data = await response.json();
    return data; 
}

//funcion que se autoinvoca
//cuando cargue el archivo se va a ejecutar
(async ()=>{
    try{
        const videos = await fetchData(API);
        //crearemos un template en html para que itere por los elementos de la respuesta
        //view es esa porcion de html
        //usamos js para iterar 
        //en esta API , para acceder a los videos, se refiere a items, se hace un map para devolver un nuevo arreglo con el template por cada resultado
        let view = `
        ${videos.items.map(video=>`
            <div class="group relative">
            <div
                class="w-full bg-gray-200 aspect-w-1 aspect-h-1 rounded-md overflow-hidden group-hover:opacity-75 lg:aspect-none">
                <img src="${video.snippet.thumbnail.high.url}" alt="${video.snippet.description}" class="w-full">
            </div>
            <div class="mt-4 flex justify-between">
                <h3 class="text-sm text-gray-700">
                <span aria-hidden="true" class="absolute inset-0"></span>
                ${video.snippet.title}
                </h3>
            </div>
            </div>
        `).slice(0,4).join('')}//para iterar solo 4 videos
            
        `;
    }catch{

    }
})();
	

Si necesitas encontrar el ID de un canal de YouTube te explico 1) Abre la p谩gina del canal en YouTube. 2) Haz clic derecho y selecciona 鈥榁iew Page Source鈥 para ver el c贸digo fuente de la p谩gina. 3) Una vez en el c贸digo fuente, presiona Ctrl + F en Windows y busca 鈥榟ref鈥. El ID del canal suele estar ubicado despu茅s de la palabra 鈥榗hannel鈥.

Voy hacer la implementacion con otra API.

Espero que tenga Exito!

Por cierto buena clase!!

He hecho la landing page the Ariana Grande, no tenia fotografias horizontales de mi mismo. Todas verticales para usar en Instagram stories. LOL

Este es el c贸digo que copia de HTML por si a alguien le sirve

      <div class="group relative">
        <div
          class="w-full bg-gray-200 aspect-w-1 aspect-h-1 rounded-md overflow-hidden group-hover:opacity-75 lg:aspect-none">
          <img src="" alt="" class="w-full">
        </div>
        <div class="mt-4 flex justify-between">
          <h3 class="text-sm text-gray-700">
            <span aria-hidden="true" class="absolute inset-0"></span>
            Title
          </h3>
        </div>
      </div>

Tuve un problema de asincronismo, ya que la carga del archivo de javascript se realizaba antes de que se completara la carga del html, por ende, cuando iba a buscar el id content, no lo referenciaba y quedaba nulo.

Encontr茅 estas 3 soluciones para este problema:

Usar el atributo defer en la etiqueta de script:
El atributo defer le indica al navegador que el archivo JavaScript se debe cargar de forma as铆ncrona y que se debe ejecutar despu茅s de que el documento HTML se haya cargado completamente. Esto permite que el archivo JavaScript se cargue antes de que se renderice el contenido de la p谩gina, pero a煤n as铆 se ejecutar谩 despu茅s de que se haya cargado todo el HTML.
Ejemplo:

<head>
  <script defer src="archivo.js"></script>
</head>

Usar el atributo async en la etiqueta de script:
El atributo async le indica al navegador que el archivo JavaScript se debe cargar de forma as铆ncrona y que se debe ejecutar tan pronto como est茅 disponible. Esto significa que el archivo JavaScript se cargar谩 y se ejecutar谩 en segundo plano, sin bloquear la carga del resto de la p谩gina. Sin embargo, esto tambi茅n significa que el archivo JavaScript se ejecutar谩 antes de que se cargue todo el HTML, lo que puede causar problemas si el JavaScript depende del contenido HTML.
Ejemplo:

<head>
  <script async src="archivo.js"></script>
</head>

O tambi茅n se puede situar la carga del archivo al final del archivo HTML, justo antes del cierre de la etiqueta </body>

Buena clase! Ahora me dispongo a implementar otra API, para comprobar los conocimientos adquiridos, espero tener suerte y poder lograrlo!

deberian actualizar el curso o la clase porque al buscar y copiar el codigo en el minuto 14:49 es muy diferente el que sale en el video y otro el que encuentro tanto en git hub como en los recursos de la clase, asi quedo mas perdido

me llego una alerta de GitGuardian, le铆 que debo sacarla o encriptarla, est谩 el git ignore, pero ese archivo main.js tiene toda la logica, no puedo hacer que lo ignone, menos s铆 despues estar谩 en GitPages
驴Qu茅 debo hacer? 驴nada?

Recursividad?

RapidAPI es una plataforma 煤nica que me permite conectarme con una gran colecci贸n de APIs p煤blicas para ayudar a impulsar mi proceso de desarrollo. Adem谩s, su mercado avanzado permite personalizar y probar diferentes tipos de API. Estas APIs pueden ser implementadas en mis proyectos. S贸lo tengo que registrarme con ellos y empezar a usar su capa gratuita, la cual me facilitar谩 el acceso a muchas APIs gratuitas. Tambi茅n me permitir谩 tener a disposici贸n, una serie de elementos ya listos, dependiendo mi caso de uso o necesidad. La capa de pago da m谩s posibilidades/implementaciones, las cuales pueden ser llevadas a proyectos reales. https://rapidapi.com/

Les dejo un link de github con una lista de links de APIS publicas de todo tipo de contenido como videojuegos, cocina, financiero y demas:
Apis Variadas

Empec茅 a jugar con la API y me cost贸, pero se me hizo interesante 馃槢

Mis apuntes en Notion 馃槃

A B C de las A .P. I.

Para el reto solo program茅 que el catch, cuando falle, cree un h1 con un mensaje de error usando innerHTML

catch (err) {
        console.log(err)
        content.innerHTML = `<h1 style="color:black;"> Lo siento, hubo un error :( </h1>`;
    }

Lo intent茅 hacer con otra API porque en ese sitio web me piden datos de tarjeta de cr茅dito, y qued茅 mas perdido que antes 馃槮

Pense que || siempre devolvia un valor booleano, pero aca se usa distinto, asi que le pregunte a la IA Chat GPt y esto me respondio:

En JavaScript, el operador || no siempre devuelve un valor booleano. En realidad, este operador devuelve el primer valor 鈥渧erdadero鈥 (truthy) que encuentre en la cadena de expresiones que est谩 evaluando.

Por ejemplo, si tienes una expresi贸n como valor1 || valor2 || valor3, JavaScript eval煤a cada uno de los valores y devuelve el primer valor que sea 鈥渧erdadero鈥 (truthy). Si ninguno de los valores es 鈥渧erdadero鈥, se devuelve el 煤ltimo valor.

Aqu铆 hay algunos ejemplos que demuestran c贸mo funciona el operador || en JavaScript:

//Javascript
console.log(1 || 2); // 1
console.log(null || 0); // 0
console.log(undefined || 'hola'); // 'hola'
console.log('' || false || 'hola'); // 'hola'
En el primer ejemplo, la expresi贸n 1 || 2 devuelve 1 porque 1 es "verdadero" (truthy) y se eval煤a antes que 2.

En el segundo ejemplo, la expresi贸n null || 0 devuelve 0 porque null no es 鈥渧erdadero鈥 (falsy) y 0 es el 煤ltimo valor en la cadena.

En el tercer ejemplo, la expresi贸n undefined || 鈥榟ola鈥 devuelve 鈥榟ola鈥 porque undefined es 鈥渇alsy鈥 y 鈥榟ola鈥 es el primer valor 鈥渧erdadero鈥 (truthy) en la cadena.

En el cuarto ejemplo, la expresi贸n 鈥樷 || false || 鈥榟ola鈥 devuelve 鈥榟ola鈥 porque 鈥樷 es 鈥渇alsy鈥, false es 鈥渇alsy鈥 y 鈥榟ola鈥 es el primer valor 鈥渧erdadero鈥 (truthy) en la cadena.

el curso por el momento me parece excelente! lo uncio con lo que no estoy muy de acuerdo es con la utilizacion de tailwind, claramente si seguimos la ruta de aprendizaje creada por platzi estaria bueno que utilicemos los metodos que fuimos aprendiendo, todo lo demas me parecio excelente las explicaciones de Oscar.

Como recomendacion se deberia hacer mucho mas enfasis en la explicacion, porque para lo que esta haciendo el profe prefiero directamente el codigo

Una clase de 馃挬

Que buena explicacion

Excelente clase ! , explica muy bien los conceptos anteriores y a帽ade los paso a paso de forma clara