in

Creación de aplicaciones móviles con React Native y WordPress

WordPress puede funcionar como una excelente plataforma de back-end para tu próxima aplicación nativa, especialmente si está impulsada por contenido o una tienda en línea. En este artículo, aprenderás los fundamentos para crear aplicaciones móviles con React Native y WordPress.

Como desarrolladores web, es posible que hayas pensado que el desarrollo de aplicaciones móviles requiere una nueva curva de aprendizaje con otro lenguaje de programación. Quizás sea necesario agregar Java y Swift a tu conjunto de habilidades para comenzar a funcionar tanto con iOS como con Android, y eso podría atascarte. ¡Pero si piensas de esa forma, este artículo te va a sorprender! Vamos a ver cómo crear una aplicación de comercio electrónico para iOS y Android utilizando la plataforma WooCommerce como nuestro backend. Este sería un punto de partida ideal para cualquiera que desee ingresar al desarrollo nativo multiplataforma.

Una breve historia del desarrollo multiplataforma  #

Comienza 2011 y vemos arranca del desarrollo de aplicaciones móviles híbridas. Los marcos como Apache Cordova, PhoneGap y Ionic Framework man emergiendo lentamente. Todo se ve bien y los desarrolladores web están codificando ansiosamente las aplicaciones móviles con los conocimientos existentes. Sin embargo, las aplicaciones móviles todavía parecían versiones móviles de sitios web. No hay diseños nativos como el diseño de material de Android o el aspecto plano de iOS. La navegación funciona de manera similar a la web y las transiciones no eran precisamente muy fluidas. Los usuarios no estaban satisfechos con las aplicaciones creadas con el enfoque híbrido y soñaban con la experiencia nativa. Avanzamos rápido hasta marzo de 2015, y React Native aparece en escena. Los desarrolladores pueden crear aplicaciones multiplataforma nativas utilizando React, una de las bibliotecas de JavaScript favoritas de muchos desarrolladores. Ahora pueden aprender fácilmente una pequeña biblioteca además de lo que saben con JavaScript. Con este conocimiento, los desarrolladores ahora apuntan a la web, iOS y Android. Además, los cambios realizados en el código durante el desarrollo se cargan en los dispositivos de prueba casi al instante. Esto solía llevar varios minutos cuando teníamos desarrollo nativo a través de otros modos de enfoque. Los desarrolladores pueden disfrutar de la retroalimentación instantánea que solían amar con el desarrollo web. Los desarrolladores de React están más que felices de poder usar los patrones existentes que han seguido en una nueva plataforma por completo. De hecho, apuntan a dos plataformas más con lo que ya conocen muy bien. Todo esto es bueno para el desarrollo front-end. Pero, ¿qué opciones tenemos para la tecnología de back-end? ¿Todavía tenemos que aprender un nuevo lenguaje o marco?

La API REST de WordPress  #

A finales de 2016, WordPress lanzó la tan esperada API REST en su núcleo y abrió las puertas a soluciones con backends desacoplados. Por lo tanto, si ya tienes un sitio web de WordPress y WooCommerce y deseas conservar exactamente las mismas ofertas y perfiles de usuario en tu sitio web y aplicación nativa, ¡este artículo es para ti!

Supuestos hechos en este artículo  #

Te guiaré a través del uso de tu habilidad de WordPress para crear una aplicación móvil con una tienda WooCommerce usando React Native. El artículo asume que:

  • Estás familiarizado con las diferentes API de WordPress, al menos a nivel principiante.
  • Estás familiarizado con los conceptos básicos de React.
  • Tienes listo un servidor de desarrollo de WordPress. Yo uso Ubuntu con Apache.
  • Tiene un dispositivo Android o iOS para llevar a cabo las pruebas mediante Expo.

Qué construiremos en este tutorial  #

El proyecto que vamos a construir a través de este artículo es una aplicación de tienda de moda. La aplicación tendrá las siguientes funcionalidades:

  • Página de la tienda que enumera todos los productos.
  • Página de un solo producto con detalles del artículo seleccionado.
  • Función “Agregar al carrito”.
  • Función “Mostrar artículos en el carrito”.
  • Función “Eliminar artículo del carrito”.

Este artículo tiene como objetivo inspirarte a utilizar este proyecto como punto de partida para crear aplicaciones móviles complejas utilizando React Native. Nota: Para obtener la aplicación completa, puede visitar el siguiente proyecto en Github y clonarlo.

Empezando con nuestro proyecto  #

Comenzaremos a construir la aplicación según la documentación oficial de React Native. Una vez instalado Node en tu entorno de desarrollo, abre símbolos del sistema y escriba el siguiente comando para instalar la aplicación Create React Native a nivel mundial.

npm install -g create-react-native-app

A continuación, podemos crear nuestro proyecto.

create-react-native-app react-native-woocommerce-store

Esto creará un nuevo proyecto React Native que podemos probar con Expo. A continuación, necesitaremos instalar la aplicación Expo en nuestro dispositivo móvil que queremos probar. Está disponible tanto para iOS como para Android. Una vez instalada la aplicación Expo, podemos ejecutar npm start en nuestra máquina de desarrollo.

cd react-native-woocommerce-store
npm start
Iniciar un proyecto de React Native a través de la línea de comandos a través de Expo. (Vista previa grande)

Después de eso, puedes escanear el código QR a través de la aplicación Expo o ingresar la URL dada en la barra de búsqueda de la aplicación. Esto ejecutará la aplicación básica ‘Hello World’ en el móvil. Ahora podemos editar App.js para realizar cambios instantáneos en la aplicación que se ejecuta en el teléfono. Alternativamente, puedes ejecutar la aplicación en un emulador. Pero para mayor brevedad y precisión, cubriremos la ejecución en un dispositivo real. A continuación, instalemos todos los paquetes necesarios para la aplicación usando este comando:

npm install -s axios react-native-htmlview react-navigation react-redux redux redux-thunk

Configuración de un sitio de WordPress  #

Dado que este artículo trata sobre la creación de una aplicación React Native, no entraremos en detalles sobre la creación de un sitio de WordPress. Consulte este artículo sobre cómo instalar WordPress en Ubuntu. Como la API REST de WooCommerce requiere HTTPS, asegúrate de que esté configurada con Let’s Encrypt. Consulta este artículo para obtener una guía práctica. No estamos creando una instalación de WordPress en localhost ya que ejecutaremos la aplicación en un dispositivo móvil y también porque se necesita HTTPS. Una vez que WordPress y HTTPS se hayan configurado correctamente, podemos instalar el complemento WooCommerce en el sitio.

Instalando el complemento WooCommerce en nuestra instalación de WordPress. (Vista previa grande)

Después de instalar y activar el complemento, continúa con la configuración de la tienda WooCommerce siguiendo el asistente. Una vez finalizado el asistente, haga clic en “Volver al panel de control”. Serás recibido por otro mensaje.

Agregar productos de ejemplo a WooCommerce. (Vista previa grande)

Haz clic en “Vamos”(Let’s go) y en “Agregar productos de ejemplo (Add example products). Esto nos ahorrará el tiempo de crear nuestros propios productos para mostrarlos en la aplicación.

Número de archivo de constantes # 

Para cargar los productos de nuestra tienda desde la API REST de WooCommerce, necesitamos las claves relevantes en su lugar dentro de nuestra aplicación. Para ello, podemos disponer de un archivo constans.js. Primero crea una carpeta llamada ‘src’ y crea subcarpetas dentro de la siguiente manera:

Cree el archivo ‘Constants.js’ dentro de la carpeta constans. (Vista previa grande)

Ahora, genetaremos las claves para WooCommerce. En el panel de WordPress, ve a WooCommerce → Configuración → API → Claves / Aplicaciones y haz clic en ‘Agregar clave’. A continuación, crea una clave de solo lectura con el nombre React Native. Copia la ConsumerKey y la ConsumerSecret en el archivo constants.js de la siguiente manera:

const Constants = {
   URL: {
wc: 'https://woocommerce-store.on-its-way.com/wp-json/wc/v2/'
   },
   Keys: {
ConsumerKey: 'CONSUMER_KEY_HERE',
ConsumerSecret: 'CONSUMER_SECRET_HERE'
   }
}
export default Constants;

Comenzando con React Navigation  #

React Navigation es una solución comunitaria para navegar entre las diferentes pantallas y es una biblioteca independiente. Permite a los desarrolladores configurar las pantallas de la aplicación React Native con solo unas pocas líneas de código. Hay diferentes métodos de navegación dentro de React Navigation:

  • Apilar.
  • Cambiar.
  • Pestañas.
  • Cajón.
  • y más.

Para nuestra Aplicación usaremos una combinación de StackNavigation y DrawerNavigation para navegar entre las diferentes pantallas. StackNavigation es similar a cómo funciona el historial del navegador en la web. Lo usamos porque proporciona una interfaz para el encabezado y los iconos de navegación del encabezado. Tiene push y pop similar a las pilas en estructuras de datos. Push significa que agregamos una nueva pantalla en la parte superior de la pila de navegación. Pop elimina una pantalla de la pila. El código muestra que StackNavigation, de hecho, alberga el DrawerNavigation dentro de sí mismo. También toma propiedades para el estilo del encabezado y los botones del encabezado. Estamos colocando el botón del cajón de navegación a la izquierda y el botón del carrito de compras a la derecha. El botón del cajón enciende y apaga el cajón, mientras que el botón del carrito lleva al usuario a la pantalla del carrito de compras.

const StackNavigation = StackNavigator({
 DrawerNavigation: { screen: DrawerNavigation }
}, {
   headerMode: 'float',
   navigationOptions: ({ navigation, screenProps }) => ({
     headerStyle: { backgroundColor: '#4C3E54' },
     headerTintColor: 'white',
     headerLeft: drawerButton(navigation),
     headerRight: cartButton(navigation, screenProps)
   })
 });

const drawerButton = (navigation) => (
 <Text
   style={{ padding: 15, color: 'white' }}
   onPress={() => {
     if (navigation.state.index === 0) {
       navigation.navigate('DrawerOpen')
     } else {
       navigation.navigate('DrawerClose')
     }
   }
   }> (
 <Text style={{ padding: 15, color: 'white' }}
   onPress={() => { navigation.navigate('CartPage') }}
 >
   <EvilIcons name="cart" size={30} />
   {screenProps.cartCount}
 </Text>
);

DrawerNavigation por otro lado dispone del cajón lateral que nos permitirá navegar entre Inicio, Tienda y Carrito. Las listas DrawerNavigator de las diferentes pantallas que el usuario puede visitar, es decir, la página de inicio, página de los productos, la página del producto, y la página de compra. También tiene una propiedad que tomará el contenedor del cajón: el menú deslizante que se abre al hacer clic en el menú de navegación móvil.

const DrawerNavigation = DrawerNavigator({
 Home: {
   screen: HomePage,
   navigationOptions: {
     title: "RN WC Store"
   }
 },
 Products: {
   screen: Products,
   navigationOptions: {
     title: "Shop"
   }
 },
 Product: {
   screen: Product,
   navigationOptions: ({ navigation }) => ({
     title: navigation.state.params.product.name
   }),
 },
 CartPage: {
   screen: CartPage,
   navigationOptions: {
     title: "Cart"
   }
 }
}, {
   contentComponent: DrawerContainer
 });
Izquierda: La página de inicio (homepage.js). Derecha: el cajón abierto (DrawerContainer.js).

Inyectando la tienda Redux en App.js #

Dado que estamos usando Redux en esta aplicación, tenemos que inyectar la tienda en nuestra aplicación. Hacemos esto con la ayuda del componente Provider.

const store = configureStore();

class App extends React.Component {
 render() {
   return (
     <Provider store={store}>    
       <ConnectedApp />    
     </Provider>    
   )
 }
}

Luego tendremos un componente ConnectedApp para que podamos tener el recuento del carrito en el encabezado.

class CA extends React.Component {
 render() {
   const cart = {
     cartCount: this.props.cart.length
   }
   return (
     <StackNavigation screenProps={cart} />
   );
 }
}

function mapStateToProps(state) {
 return {
   cart: state.cart
 };
}

const ConnectedApp = connect(mapStateToProps, null)(CA);

Redux Store, acciones y reductores #

En Redux, tenemos tres partes diferentes:

  1. Store: Contiene el estado completo de toda tu aplicación. La única forma de cambiar el estado es enviarle una acción.
  2. Acciones: Un objeto simple que representa la intención de cambiar el estado.
  3. Reductores: Una función que acepta un estado y un tipo de acción y devuelve un nuevo estado.

Estos tres componentes de Redux nos ayudaran a lograr un estado predecible para toda la aplicación. Para simplificar, veremos cómo se obtienen y guardan los productos en la tienda Redux. En primer lugar, veamos el código para crear la tienda:

let middleware = [thunk];

export default function configureStore() {
    return createStore(
        RootReducer,
        applyMiddleware(...middleware)
    );
}

A continuación, la acción de productos es responsable de obtener los productos del sitio web remoto.

export function getProducts() {
   return (dispatch) => {
       const url = `${Constants.URL.wc}products?per_page=100&consumer_key=${Constants.Keys.ConsumerKey}&consumer_secret=${Constants.Keys.ConsumerSecret}`

       return axios.get(url).then(response => {
           dispatch({
               type: types.GET_PRODUCTS_SUCCESS,
               products: response.data
           }
       )}).catch(err => {
           console.log(err.error);
       })
   };
}

El reductor de productos es responsable de devolver la carga útil de datos y si es necesario modificarlos.

export default function (state = InitialState.products, action) {
    switch (action.type) {
        case types.GET_PRODUCTS_SUCCESS:
            return action.products;
        default:
            return state;
    }
}

Visualización de la tienda WooCommerce #

El archivo products.js es nuestra página de la Tienda. Básicamente, muestra la lista de productos de WooCommerce.

class ProductsList extends Component {

 componentDidMount() {
   this.props.ProductAction.getProducts(); 
 }

 _keyExtractor = (item, index) => item.id;

 render() {
   const { navigate } = this.props.navigation;
   const Items = (
     <FlatList contentContainerStyle={styles.list} numColumns={2}
       data={this.props.products || []} 
       keyExtractor={this._keyExtractor}
       renderItem={
         ({ item }) => (
           <TouchableHighlight style={{ width: '50%' }} onPress={() => navigate("Product", { product: item })} underlayColor="white">
             <View style={styles.view} >
               <Image style={styles.image} source={{ uri: item.images[0].src }} />
               <Text style={styles.text}>{item.name}</Text>
             </View>
           </TouchableHighlight>
         )
       }
     />
   );
   return (
     <ScrollView>
       {this.props.products.length ? Items :
         <View style={{ alignItems: 'center', justifyContent: 'center' }}>
           <Image style={styles.loader} source={LoadingAnimation} />
         </View>
       }
     </ScrollView>
   );
 }
}

this.props.ProductAction.getProducts()y this.props.products son posibles gracias a mapStateToProps y mapDispatchToProps.

Pantalla de listado de productos. (Vista previa grande)

mapStateToProps y mapDispatchToProps #

State es la tienda de Redux y Dispatch son las acciones que disparamos. Ambos se expondrán como accesorios en el componente.

function mapStateToProps(state) {
 return {
   products: state.products
 };
}
function mapDispatchToProps(dispatch) {
 return {
   ProductAction: bindActionCreators(ProductAction, dispatch)
 };
}
export default connect(mapStateToProps, mapDispatchToProps)(ProductsList);

Estilos  #

En React, los estilos nativos generalmente se definen en la misma página. Es similar a CSS, pero usamos propiedades camelCase en lugar de propiedades con guiones.

const styles = StyleSheet.create({
 list: {
   flexDirection: 'column'
 },
 view: {
   padding: 10
 },
 loader: {
   width: 200,
   height: 200,
   alignItems: 'center',
   justifyContent: 'center',
 },
 image: {
   width: 150,
   height: 150
 },
 text: {
   textAlign: 'center',
   fontSize: 20,
   padding: 5
 }
});

Número de página de producto único # 

Esta página contiene detalles de un producto seleccionado. Muestra al usuario el nombre, precio y descripción del producto. También tiene la función “Agregar al carrito”.

Página de un solo producto. (Vista previa grande)

Página del Carrito #

Esta pantalla muestra la lista de artículos en el carrito. La acción tiene las funciones getCart, addToCart y removeFromCart. El reductor maneja las acciones de la misma manera. La identificación de acciones se realiza a través de actionTypes: constantes que describen la acción que se almacenan en un archivo separado.

export const GET_PRODUCTS_SUCCESS = 'GET_PRODUCTS_SUCCESS'
export const GET_PRODUCTS_FAILED = 'GET_PRODUCTS_FAILED';

export const GET_CART_SUCCESS = 'GET_CART_SUCCESS';
export const ADD_TO_CART_SUCCESS = 'ADD_TO_CART_SUCCESS';
export const REMOVE_FROM_CART_SUCCESS = 'REMOVE_FROM_CART_SUCCESS';

Este es el código del componente CartPage:

class CartPage extends React.Component {

 componentDidMount() {
   this.props.CartAction.getCart();
 }

 _keyExtractor = (item, index) => item.id;

 removeItem(item) {
   this.props.CartAction.removeFromCart(item);
 }

 render() {
   const { cart } = this.props;
   console.log('render cart', cart)

   if (cart && cart.length > 0) {
     const Items = <FlatList contentContainerStyle={styles.list}
       data={cart}
       keyExtractor={this._keyExtractor}
       renderItem={({ item }) =>
         <View style={styles.lineItem} >
           <Image style={styles.image} source={{ uri: item.image }} />
           <Text style={styles.text}>{item.name}</Text>
           <Text style={styles.text}>{item.quantity}</Text>
           <TouchableOpacity style={{ marginLeft: 'auto' }} onPress={() => this.removeItem(item)}><Entypo name="cross" size={30} /></TouchableOpacity>
         </View>
       }
     />;
     return (
       <View style={styles.container}>
         {Items}
       </View>
     )
   } else {
     return (
       <View style={styles.container}>
         <Text>Cart is empty!</Text>
       </View>
     )
   }
 }
}

Como puedes ver, estamos usando un FlatList para iterar a través de los artículos del carrito. Coge una matriz y crea una lista de elementos que se mostrarán en la pantalla.

Izquierda: la página del carrito cuando tiene artículos. Derecha: La página del carrito cuando está vacía.

Conclusión  #

Puedes configurar información sobre la aplicación, como el nombre y el icono en el archivo app.json. La aplicación se puede publicar después de la instalación de npm exp. Para resumir:

  • Ahora tenemos una aplicación de comercio electrónico decente con React Native.
  • Expo se puede utilizar para ejecutar el proyecto en un teléfono móvil Android e iOS.
  • Se pueden utilizar tecnologías de backend existentes como WordPress.
  • Redux se puede utilizar para administrar el estado de toda la aplicación.
  • Los desarrolladores web, especialmente los desarrolladores de React, pueden aprovechar este conocimiento para crear aplicaciones más grandes.

Para obtener la aplicación completa, puedes visitar este proyecto en Github y clonarlo. Siéntete libre de bifurcarlo y mejorarlo aún más. Como ejercicio, puedes continuar incorporando más funciones al proyecto, como:

  • Página de pago.
  • Autenticación.
  • Almacenar los datos del carrito en AsyncStorage para que al cerrar la aplicación no se borre el carrito.

¿Qué opinas?

Escrito por Wombat

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *

Una guía completa para WordPress multisitio

Revisión de LifterLMS: ¿el mejor complemento LMS de WordPress? (2021)