No tienes acceso a esta clase

¡Continúa aprendiendo! Únete y comienza a potenciar tu carrera

Curso Práctico de React.js

Curso Práctico de React.js

Oscar Barajas Tavares

Oscar Barajas Tavares

React Context

22/30
Recursos

Aportes 34

Preguntas 16

Ordenar por:

¿Quieres ver más aportes, preguntas y respuestas de la comunidad?

o inicia sesión.

useContext

Context es una herramienta para pasar propiedades en un arbol de componentes de arriba hacia abjo sin tener que pasar por componentes intermedios.

Par usar context debemos importar dos cosas:
createContext -> Permite crear el contexto
useContext -> Este hook nos va permitir uusar contextos dentro de los componentes

import { createContext, useContext} from 'react'; // Tambien podemos importarlo de esta manera
// Creando el contexto
const Context = createContext('valor');

createContext recibe un valor inicial que se va seleccionar en caso de no tener un provider. Puede ser cualquier valor (string, number, objeto, array…)

¿Que es un provider?

Es el encargado de poder pasar el contexto hacia los componentes hijos

import { createContext, useContext} from 'react';

//creando el contexto
const Context = createContext('valor por defecto'); 
const Provider = ({children} => {
	return (
//Recibe un valor obligatorio que es el que se va estar pasando a los componentes hijos****
	<Context.Provider value={"soy un valor"} > 
				{children}
		  </Context.Provider>
	)
}

//Finalmente usamos nuestro componente Provider

function App() {
	return (
	<Provider>
			<Contenido>
		</Provider>
	);
}

export default App;

Líneas de viento de un huracán en ciernes

estoy mareao

¿Qué es react context?

React context es una manera de acceder a un tipo de “variables globales” entre nuestros componentes de react. Es decir, hay situaciones en las que quisieramos pasarles datos importantes a un componente de react, y a todos sus nodos hijos. Sin embargo, usando props esta tarea es muy repetitiva y poco efectiva de mantener. Incluso, existen ocasiones que le pasamos props a nodos obligadamente aunque nunca la necesiten. Es aquí cuando entra en acción react context. Nosostros podemos acceder desde donde sea a una variables en nuestra aplicación. E inlcuso podemos crear cuantos contexto queramos donde cada uno mantendra información necesaria.

ala… así no se explican las bases de uso de un elemento tan complicado. Esto estaría muchísimo mejor primero explicarlo en un solo documento, despacio y sin tanto lenguaje decorativo, experimentando cada elemento, y no “ir aplicando y explicando al tiempo”.

Creo que esta clase debe de tener parte 2 o por lo menos ver el video dos veces para poder entender mejor

Me tomo unpar de horas y ver esta clase varias veces para darme cuenta que tenia un error, les comparto por si acaso:
.
codigo con error

const App = () => {
    const initialState = useInitialState(); //Este hook retorna state y addToCart
    return (
        <AppContext.Provider value={'initialState'}>
            <BrowserRouter>
                <Layout>
                    <Routes>

Le pase el valor de inicial state como cadena texto y eso me tomo par de horas entender que pasaba.
.

Como dijo el profesor anterior “Ojo con esto! que sino, no les va a funcionar !!”

.
lo correcto es

const App = () => {
    const initialState = useInitialState(); //Este hook retorna state y addToCart
    return (
        <AppContext.Provider value={initialState}>
            <BrowserRouter>
                <Layout>
                    <Routes>

Hasta ahora venía entendiendo algunos hooks explicados en las clases pasadas. Sin embargo, en esta clase siento que casi no entendí nada. Se usan muchos elementos de un lado a otro y se mueven muy rápido. No logré comprender cómo se usa, cómo es la sintaxis, tampoco la parte donde usó el spread operator. En esta clase me parece que da un salto muy grande como de resolver ecuaciones lineales de una variable (tipo secundaria) a pasar a resolver ecuaciones diferenciales.

Antes de dar mi explicación, quisiera dar un poco de contexto.

Dentro de esta clase se crea useInitialState, un costume hook que contendrá la lógica de la aplicación, y Appcontext. Este ultimo es el que realmente contiene la lógica de React Context

**REACT CONTEXT: estado compartido **
Es una forma de tener acceso a datos a través del árbol de componentes sin tener que pasar props manualmente en cada nivel, usando datos globales.
Para esto tenemos un proveedor que envolverá a todos los componentes que serán los consumidores de nuestro contexto.
.
Fases:

  1. Crear el contexto de nuestra aplicación
  2. Proveer nuestro contexto con los datos que queremos globales.
  3. Consumir los datos desde cualquier parte de nuestra aplicación.

.

  • CREAR :
    Se crea una carpeta context aparte, en donde tendrán todo el contexto de su aplicación:
    Es importante crear el contexto con createContext, ya que este nos regresará dos componentes: provider y consumer.
import React from 'react';

const AppContext = React.createContext({});

export default AppContext;

Al crear el contexto también podemos pasarle un valor inicial entre paréntesis, pero en este caso lo iniciamos como un objeto vacío
.

  • PROVEER:
    Para poder proveer del contexto se utiliza el método provider del componente que hemos creado con el contexto (AppContext)
    En la carpeta root se encuentra toda la lógica de navegación de reactShop. Ahí es donde retornaremos nuestro provider con nuestro contexto en la etiqueta value.
import AppContext from '../context/AppContext';
import useInitialState from '../hooks/useInitialState';

const App = () => {
	const initialState = useInitialState();
	return (
		<AppContext.Provider value={initialState}>
	{/* todo lo que se encuentra dentro de la etiqueta AppContext.Provider podrá utilizar el contexto que se encuentra dentro de la etiqueta value */}
		</AppContext.Provider>
	);
}
  • CONSUMIR:
    useContext nos ayuda a acceder a datos globales de nuestro contexto, desde cualquier componente hijo, sin tener que pasar estos datos por props componente por componente.
    Básicamente la formula de useContext es:
import React,{useContext} from 'react'
import {context} from './direccionContexto/'

const {value} = React.useContext (context)

como por ejemplo dentro de ProductItem se obtiene addToCard usando use.context

import React, {useContext} from 'react';
import AppContext from '../context/AppContext';

const ProductItem = ({product}) => {
	const { addToCart } = useContext(AppContext);

	const handleClick = item => {
		addToCart(item);
	}
	console.log (product)
	return (
				<figure onClick= {()=> handleClick(product)} >
					<img src={addToCartImage} alt="" />
				</figure>
	);
}

Espero haber aclarado un poco las dudas de esta clase.

He avanzado en el curso, he resuelto los problemas que se han presentado, igual siento que NO explica nada, y no estoy entendiendo realmente lo que estoy haciendo…

Clases como esta me refuerzan la idea de que en Platzi falta mucha didactica para ensenhar a programar. Lo cual no es nada facil, ya que tambien soy profesor y se lo dificil que esto implica, pero ayudarse con una pizarra y explicar con dibujos tal cual lo que esta haciendo el codigo, es una ayuda inmensa que siempre le voy a reclamar a Platzi

Min 12:44 aparece un sonido raro de fondo que miedo.

Si son como yo y quieren ver que al presionar el botón suceda algo podemos jugar con el handleClick un ejemplo simple el console.log() 😄

const handleClick = item => {
		addToCart(item)
		console.log(item)
	}

si fuera un pokemon ya me hubiera atacado a mi mismo

Veo muchos porblemas, especialmente de falta de rigurosidad por parte del profesor para comunicar y hacer digerible el curso: no nombra las cosas que usa por su nombre técnico (atributos, elementos, métodos, constantes…), las descripciónes de su proceso y de las herramientas que usa son demasiado vagas y redundan constantemente con “muletillas” que no dicen nada.

Uno puede excusarlo diciendo “Es que para eso está la documentación” o “es que de los errores se aprende”, pero aquí mismo en Platzi he dado con profesores que de verdad motivan por la forma como transmiten el conocimiento, y no se limitan a seguir un paso a paso.

Para mi portfolio full stack, Estoy desarrollando mi primera app, con el stack MERN.

Estoy pensando meter un CRUD con el stack MERN para que el usuario cree una card para definir una emoción que siente.

Que esa card se guarde en una collection de mongo db.
(imagen de la emoción, nombre de la emoción, texto describiendo la emoción)

Creo que el uso de useReducer en combinación con useContext hacen algo muy similar a Redux…

He visto que a varios compañeros les esta pasando lo mismo que a mi y es que no aparece el contenido de la pagina principal y tampoco me puedo cambiar a otras paginas, alguien seria tan amable de informarme por que se esta produciendo este error, cabe aclarar que lo ultimo que hice fue clonar el proyecto del profesor pero el problema continua muchas gracias

![](

hola que tal , queria saber que posible error pude haber cometido

import React from 'react';
import { BrowserRouter, Switch, Route } from 'react-router-dom';
import Layout from '@containers/Layout';
import Home from '@pages/Home';
import Login from '@pages/Login';
import RecoveryPassword from '@pages/RecoveryPassword';
import SendEmail from '@pages/SendEmail';
import NewPassword from '@pages/NewPassword';
import MyAccount from '@pages/MyAccount';
import CreateAccount from '@pages/CreateAccount';
import Checkout from '@pages/Checkout';
import Orders from '@pages/Orders';
import NotFound from '@pages/NotFound';
import AppContext from '@context/AppContext';
import useInitialState from '@hooks/useInitialState';
import '@styles/global.css';

const App = () => {
	const initialState = useInitialState();
	return (
		<AppContext.Provider value = {initialState}>
		<BrowserRouter>
			<Layout>
				<Switch>
					<Route exact path="/" component={Home} />
					<Route exact path="/login" component={Login} />
					<Route exact path="/recovery-password" component={RecoveryPassword} />
					<Route exact path="/send-email" component={SendEmail} />
					<Route exact path="/new-password" component={NewPassword} />
					<Route exact path="/account" component={MyAccount} />
					<Route exact path="/signup" component={CreateAccount} />
					<Route exact path="/checkout" component={Checkout} />
					<Route exact path="/orders" component={Orders} />
					<Route path="*" component={NotFound} />
				</Switch>
			</Layout>
		</BrowserRouter>
		</AppContext.Provider>
	);
}

export default App;
import React, { useContext } from 'react';
import '@styles/ProductItem.scss';
import AppContext from '@context/AppContext';
import addToCartImage from '@icons/bt_add_to_cart.svg';

const ProductItem = ({ product }) => {
	const { addToCart } = useContent(AppContext);

	const handleClick = item => {
		addToCart(item);
	}
	return (
		<div className="ProductItem">
			<img src={product.images[0]} alt={product.title} />
			<div className="product-info">
				<div>
					<p>${product.price}</p>
					<p>{product.title}</p>
				</div>
				<figure onClick={ () => handleClick(product)} >
					<img src={addToCartImage} alt="" />
				</figure>
			</div>
		</div>
	);
}


export default ProductItem;
import { useState } from "react";

const initialState = {
    cart: [],
}

const useInitialState = () => {
    const [state,setState] = useState(initialState);

    const addToCart = (payload) => {
        setState({
            ...state,
            cart: [...state.cart, payload]
        });
    };

    return{
        state,
        addToCart
    }

}

export default useInitialState;

const path = require('path');
const HtmlWebpackPlugin = require ('html-webpack-plugin');
const MiniCssExtractPlugin = require('mini-css-extract-plugin');

module.exports = {
    entry: './src/index.js',
    output: {
        path: path.resolve(__dirname, 'dist'),
        filename: 'bundle.js',
        publicPath: '/',
    },
    mode: 'development',
    resolve:{
        extensions:['.js','.jsx'],
        alias:{
            '@components': path.resolve(__dirname, 'src/components'),
            '@containers': path.resolve(__dirname, 'src/containers'),
            '@pages': path.resolve(__dirname,'src/pages/'),
            '@styles': path.resolve (__dirname,'src/styles/'),
            '@icons': path.resolve(__dirname, 'src/assets/icons/'),
            '@logos': path.resolve(__dirname,'src/assets/logos/'),
            '@hooks': path.resolve(__dirname, 'src/hooks/'),
            '@context': path.resolve(__dirname, 'src/context/')
        }
    },
    module:{
        rules: [
            {
                test: /\.(js|jsx)$/,
                exclude: /node_modules/,
                use:{
                    loader:'babel-loader'
                }
            },
            {
                test: /\.html$/,
                use: [
                    {
                        loader:'html-loader',
                    }
                ]
            },
            {
                test: /\.(css|scss)$/,
                use:[
                    "style-loader",
                    "css-loader",
                    "sass-loader",
                ],
            },
            {
                test: /\.(png|svg|jpg|gif)$/,
                type:'asset'
            }
        ]
    },
    plugins:[
        new HtmlWebpackPlugin({
            template: './public/index.html',
            filename: './index.html'
        }),
        new MiniCssExtractPlugin({
            filename:'[name].css'
        }),
    ],
    devServer:{
        historyApiFallback: true,
    }
}
import React from 'react';

const AppContext = React.createContext({});

export default AppContext;

Context provee una forma de pasar datos a través del árbol de componentes sin tener que pasar props manualmente en cada nivel.

En una aplicación típica de React, los datos se pasan de arriba hacia abajo (de padre a hijo) a través de props, pero esta forma puede resultar incómoda para ciertos tipos de props (por ejemplo, localización, el tema de la interfaz) que son necesarias para muchos componentes dentro de una aplicación. Context proporciona una forma de compartir valores como estos entre componentes sin tener que pasar explícitamente una prop a través de cada nivel del árbol.

class App extends React.Component {
  render() {
    return <Toolbar theme="dark" />;
  }
}

function Toolbar(props) {
  // El componente Toolbar debe tener un prop adicional "theme"
  // y pasarlo a ThemedButton. Esto puede llegar a ser trabajoso
  // si cada botón en la aplicación necesita saber el tema,
  // porque tendría que pasar a través de todos los componentes.
  return (
    <div>
      <ThemedButton theme={props.theme} />
    </div>
  );
}

class ThemedButton extends React.Component {
  render() {
    return <Button theme={this.props.theme} />;
  }
}

Usando Context podemos evitar pasar props
 a través de elementos intermedios:

// Context nos permite pasar un valor a lo profundo del árbol de componentes
// sin pasarlo explícitamente a través de cada componente.
// Crear un Context para el tema actual (con "light" como valor predeterminado).
const ThemeContext = React.createContext('light');

class App extends React.Component {
  render() {
    // Usa un Provider para pasar el tema actual al árbol de abajo.
    // Cualquier componente puede leerlo, sin importar qué tan profundo se encuentre.
    // En este ejemplo, estamos pasando "dark" como valor actual.
    return (
      <ThemeContext.Provider value="dark">
        <Toolbar />
      </ThemeContext.Provider>
    );
  }
}

// Un componente en el medio no tiene que
// pasar el tema hacia abajo explícitamente.
function Toolbar() {
  return (
    <div>
      <ThemedButton />
    </div>
  );
}

class ThemedButton extends React.Component {
  // Asigna un contextType para leer el contexto del tema actual.
  // React encontrará el Provider superior más cercano y usará su valor.
  // En este ejemplo, el tema actual es "dark".
  static contextType = ThemeContext;
  render() {
    return <Button theme={this.context} />;
  }

Increible clase con MUCHISIMA informacion para absorver, tanto del profe como de los compañeros. Veanla con mucha paciencia, repitanla las veces que sea necesario.

He leído múltiples comentarios acerca de la forma en la que se dicto esta clase, en lo personal esto es una maravilla… he estado desarrollando una App personal en react desde hace unos meses, sin conocimiento de este en absoluto, y este video valio toda la pena de el mundo. Habia conocido el Context pero nunca lo habia aplicado, no sabia lo maravilloso que es… hasta el dia de hoy he estado pasando todos los states por los props, que equivocado he estado. Me encanta esto!

Durante estos cursos de Platzi he visto mucha gente que no entiende y se queja, generalmente sólo utilizan el video como respaldo. Algo que aprendí en la Universidad es que debes LEER antes de ir a la clase, en este caso debes leeerte la documentación de context y con ello va a tener un contexto mejor y vas a comprender mejor, en la Universidad siempre se debe leer el texto guía, así entiendes mucho más rápido y te descomplicas

esta es la sexta ves que veo la clase

Que clase tan pesada, no entendí nada!

Teniendo encuenta lo realizado, los context en react se utilizan principalmente para poder pasar variables de un componente padre a un componente hijo, (esto se utiliza cuando hay muchos componentes y no es optimo pasar los prop, por que seria pasar de un componente a otro y si se tiene que agregar un valor a un componente p tendría que pasar ese valor sin ser usado por el componente a,b , c, d… y como se puede ver no es muy recomendable).

para esto Oscar crea un Appcontext que va en este caso a recibir un objeto vacío:

luego crea un useInitialState donde retorna un objeto de productos y una función de agregar un producto, la logica interna de la función los que hace es que cada vez que se llame a la función me envie un nuevo producto sin perder los productos ya existentes en ese array, es decir en cart.

el uso del useState es importante por que permite crear un objeto state y una función que modifica el valor de ese objeto “setState”.

retomando, lo que hace el objeto inicialState es inicializar el valor de state.

const inicialState={
    cart:[]
}

 const [state, setState]=useState(inicialState);

Luego en ProductItem lo que hace es mediante el hook useContext de React usar el AppContext previamente creado.

const {addToCart}= useContext(AppContext);

pero te preguntaras que hago con un context vacio, por que así se declaro en la creación de AppContext, pues bueno para poder utilizar esa función, dentro de App.jsx se utiliza el AppConext.Provider y se añade el valor initialState donde incorpora y retorna el objeto y la función

 <AppContext.Provider value={initialState}> 

esto lo que indica que toda los variables como la función va a hacer globales, lo cual cualquier componente creado como hijo del AppContext van a poder acceder tanto al objeto como a la función

Alquien mas se le hizo un poco complicado? nota mental, cuando vean un curso sigan el formato, yo quise usar TS ya que lo aprendi en un curso, pero ahora cambiare a js xd

interface ProductCardProps {
  price: number;
  name: string;
  image: string;
}

interface AppContextProps {
  addToCart: (product: ProductCardProps) => void;
  card: string[];
}

export default function ProductCard({ price, name, image }: ProductCardProps) {
  const { addToCart } = useContext(AppContext) as AppContextProps;

  function handleAddToCart(product: ProductCardProps) {
    addToCart(product);
  }

  return (
    <div className="product-card">
      <img src={image} alt={name} />
      <div className="product-info">
        <div>
          <p>{`${numberToPrice(price)}`}</p>
          <p>{name}</p>
        </div>
        <figure onClick={() => handleAddToCart({ price, name, image })}>
          <img src="./icons/bt_add_to_cart.svg" alt="carIcon" />
        </figure>
      </div>
    </div>
  );
}

¿Alguien más se desespero con el error de la imagen addToCart? casi le gritaba a la compu: es no es la variable correcta!

React Context
React Context is a way to manage state globally.

It can be used together with the useState Hook to share state between deeply nested components more easily than with useState alone.

Estoy pensando meter un CRUD con el stack MERN para que el usuario cree una card para definir una emoción que siente.

Que esa card se guarde en una collection de mongo db.
(imagen de la emoción, nombre de la emoción, texto describiendo la emoción)

¿Lo ven posible?

Casos de USO para Context

Yo siempre lo vi como un redux Lite jajajaja
.
Bueno, a lo que vi esta muy bueno para features de no gran relevancia, en este caso lo utilizamos para el carrito pero eso seria mejor con Redux.
.
CASOS DE USO: switch para dark mode, carrito de compras, contadores.

Les comparto mis apuntes. Los complementé con los aportes de algunos compañeros. Cabe destacar que en mi caso el componente de ProductItem se llama Product

Context es una herramienta para pasar propiedades en un árbol de componentes de arriba hacia abajo sin tener que pasar por componentes intermedios.

Context y Redux son cosas diferentes. Redux se encarga del flujo de la información en la aplicación, pasando por una serie de eventualidades que tienen que suceder, mientras que Context permite que la información este disponible para los diferentes componentes de la App sin tener que pasar por intermediarios.

Par usar context debemos importar dos cosas: createContext → Permite crear el contexto. useContext → Este hook nos va permitir usar contextos dentro de los componentes

import { createContext, useContext} from 'react';

//creando el contexto
const Context = createContext('valor por defecto'); 
const Provider = ({children} => {
	return (
		//Recibe un valor obligatorio que es el que se va estar pasando a los componentes hijos****
		<Context.Provider value={"soy un valor"} > 
			{children}
	  </Context.Provider>
	)
}

//Finalmente usamos nuestro componente Provider

function App() {
	return (
		<Provider>
			<Contenido>
		</Provider>
	);
}

export default App;

createContext recibe un valor inicial que se va seleccionar en caso de no tener un provider. Puede ser cualquier valor (string, number, objeto, array, etc).

El provider es el encargado de poder pasar el contexto hacia los componentes hijos.

Usar Context en la App

  • Crear carpeta context.

  • Crear un archivo para crear los context. Ej: AppContext.js

    // Crear contexto de la App
    import React from 'react';
    
    const AppContext = React.createContext({});
    
    export default AppContext;
    
  • Al definir el contexto para que pueda ser leído por otros componentes:

    ...
    import AppContext from '@context/AppContext';
    import useInitialState from '@hooks/useInitialState';
    
    const App = () => {
    	...
    	const initialState = useInitialState();
    
    	return (
            <AppContext.Provider value={ initialState }>
                <BrowserRouter>
                    <Layout>
                        <Switch>
                            <Route exact path={'/'} component={ Home } />
                            <Route exact path={'/login'} component={ Login } />
                            <Route exact path={'/password-recovery'} component={ PasswordRecovery } />
                            <Route exact path={'/send-email'} component={ SendMail } />
                            <Route exact path={'/new-password'} component={ NewPassword } />
                            <Route exact path={'/account'} component={ MyAccount } />
                            <Route exact path={'/signup'} component={ CreateAccount } />
                            <Route exact path={'/checkout'} component={ Checkout } />
                            <Route exact path={'/orders'} component={ Orders } />
                            <Route path="*" component={ NotFound } />
                        </Switch>
                    </Layout>
                </BrowserRouter>
            </AppContext.Provider>
        );
    }
    
  • En este caso se tiene un custom hook para agregar productos al carrito y guardarlos en el estado.

    // Agregar al estado los productos que se añadan al carrito
    import { useState } from "react";
    
    const initialState = {
        cart: []
    };
    
    const useInitialState = () => {
        const [state, setState] = useState(initialState);
    
        // Agregar productos al carrito
        const addToCart = (payload) => {
            // Mantiene los datos previos del state y adiciona el producto nuevo
            setState({
                ...state,
                cart: [...state.cart, payload]
            });
        };
    
        return {
            state,
            addToCart
        }
    };
    
    export default useInitialState;
    
  • Para acceder al contexto desde los componentes hijo se usa el hook useContext.

    import React, { useContext } from 'react'
    ...
    import AppContext from '@context/AppContext';
    
    const Product = ({ product }) => {
        // Obtener las propiedades del producto
        const { title, images, price } = product;
    
        // Obtener del contexto la función para agregar productos al carrito
        const { addToCart } = useContext(AppContext);
    
        // Agregar al carrito el producto seleccionado al hacer click
        const handleClick = (productItem) => {
            addToCart(productItem)
        };
    
        return (
            <div className='Product'>
                <img 
                    src={ images[0] }
                    alt={ title } 
                    className="product-img"
                />
    
                <div className="product-info">
                    <div>
                        <p>${ price }</p>
                        <p>{ title }</p>
                    </div>
    
                    <figure onClick={ () => handleClick(product) }>
                        <img 
                            src={ addToCartIcon }
                            alt="Add to cart icon"
                        />
                    </figure>
                </div>
            </div>
        );
    }
    
    export default Product
    

Para mi portfolio full stack, Estoy desarrollando mi primera app, con el stack MERN.

Estoy pensando meter un CRUD con el stack MERN para que el usuario cree una card para definir una emoción que siente.

Que esa card se guarde en una collection de mongo db.
(imagen de la emoción, nombre de la emoción, texto describiendo la emoción)

Y claro, que pueda editar el texto de la emoción y borrar la card.

¿Como hacen ustedes cuando buscan una funcionalidad nueva y entender el código?

Hola muchachos! le encontre una solucion al error que me arrojaba la aplicacion. Espero y les sirva como a mi.