Primeros pasos: Cómo escribir y también implementar tus primeras funciones

Para comenzar con Cloud Functions, prueba seguir este instructivo, que comienza con las tareas de configuración requeridas y después muestra los pasos necesarios para la creación y la implementación de dos funciones relacionadas:

  • addMessage(), que expone una URL que acepta un valor de texto y lo escribe en Realtime Database.
  • makeUppercase(), que se activa cuando se escribe en Realtime Database y convierte el texto en mayúsculas.

Elegimos Realtime Database y funciones activadas por HTTP para este ejemplo, pero existen muchas más opciones para activar funciones. Consulta las guías para los eventos de autenticación, eventos de análisis, entre otros.

Compila la muestra en el proyecto de Firebase

Las siguientes secciones de este instructivo detallan los pasos necesarios para compilar e implementar la muestra. Si solo quieres ejecutar el código e inspeccionarlo, ve a Revisa el código completo de la muestra.

Configura e inicializa el SDK de Firebase para Cloud Functions

En primer lugar, instala Firebase CLI tal como se describe en la Referencia de Firebase CLI. Firebase CLI requiere la instalación de Node.js y npm. Para instalarlos, puedes seguir las instrucciones que se encuentran en https://nodejs.org/. Cuando se instala Node.js también se instala npm.

Cloud Functions ejecuta la versión 6.14.0 de Node, por lo que te recomendamos que hagas desarrollos locales con esta versión.

Una vez que hayas instalado Node.js y npm, instala Firebase CLI a través de npm:

npm install -g firebase-tools

Esto instala el comando firebase disponible de manera global. Si el comando falla, es probable que necesites cambiar los permisos de npm. Para actualizar a la versión más reciente de firebase-tools, vuelve a ejecutar el mismo comando.

Para inicializar el proyecto:

  1. Ejecuta firebase login para acceder a través del navegador y autenticar la herramienta de Firebase.
  2. Ve al directorio de tu proyecto de Firebase.
  3. Ejecuta firebase init functions. La herramienta te ofrece una opción para instalar las dependencias con npm. Es seguro rechazarla si quieres administrar las dependencias de otra manera.
  4. La herramienta te ofrece dos opciones de idiomas:

Después de completar estos comandos de forma correcta, la estructura de tu proyecto será similar a la siguiente:

JavaScript

myproject
 +- .firebaserc    # Hidden file that helps you quickly switch between
 |                 # projects with `firebase use`
 |
 +- firebase.json  # Describes properties for your project
 |
 +- functions/     # Directory containing all your functions code
      |
      +- .eslintrc.json  # Optional file containing rules for JavaScript linting.
      |
      +- package.json  # npm package file describing your Cloud Functions code
      |
      +- index.js      # main source file for your Cloud Functions code
      |
      +- node_modules/ # directory where your dependencies (declared in
                       # package.json) are installed

TypeScript

myproject
 +- .firebaserc    # Hidden file that helps you quickly switch between
 |                 # projects with `firebase use`
 |
 +- firebase.json  # Describes properties for your project
 |
 +- functions/     # Directory containing all your functions code
      |
      +- package.json  # npm package file describing your Cloud Functions code.
      |
      +- tsconfig.json # Config file containing compiler options.
      |
      +- tslint.json   # Optional file containing rules for TypeScript linting.
      |
      +- src/     # Directory containing TypeScript source
      |   |
      |   +- index.ts     # main source file for your Cloud Functions code
      |
      +- lib/
          |
          +- index.js     # JavaScript output from TypeScript source.
          |
          +- index.js.map # Sourcemap file for TypeScript source.

Después de realizar la configuración y de inicializar tu proyecto, puedes abrir el directorio fuente y para comenzar a agregar código como se describe en las siguientes secciones.

Importa los módulos requeridos para inicializar

Para esta muestra, tu proyecto debe importar los módulos de Cloud Functions y de SDK de Admin con declaraciones require de Node. Agrega líneas como las siguientes en el archivo index.js:

// The Cloud Functions for Firebase SDK to create Cloud Functions and setup triggers.
const functions = require('firebase-functions');

// The Firebase Admin SDK to access the Firebase Realtime Database.
const admin = require('firebase-admin');
admin.initializeApp();

Estas líneas cargan los módulos firebase-functions y firebase-admin. Además, inicializan una instancia de app admin desde la cual se pueden realizar cambios de Realtime Database. Dondequiera que esté disponible la compatibilidad con el SDK de Admin, como lo es con FCM, Authentication y Firebase Realtime Database, proporciona una poderosa manera de integrar Firebase con Cloud Functions.

Firebase CLI instala automáticamente los módulos de Node de Firebase y del SDK de Firebase para Cloud Functions cuando inicializas tu proyecto. Para agregar bibliotecas de terceros a tu proyecto, puedes modificar tu functions/package.json, ejecutar npm install y realizar solicitudes como lo harías normalmente. Para obtener más información, consulta Cómo controlar dependencias.

Agrega la función addMessage()

Para la función addMessage(), agrega estas líneas a index.js:

// Take the text parameter passed to this HTTP endpoint and insert it into the
// Realtime Database under the path /messages/:pushId/original
exports.addMessage = functions.https.onRequest((req, res) => {
  // Grab the text parameter.
  const original = req.query.text;
  // Push the new message into the Realtime Database using the Firebase Admin SDK.
  return admin.database().ref('/messages').push({original: original}).then((snapshot) => {
    // Redirect with 303 SEE OTHER to the URL of the pushed object in the Firebase console.
    return res.redirect(303, snapshot.ref.toString());
  });
});

La función addMessage() es un extremo de HTTP. Cada solicitud que se envía al extremo hace que los objetos de Solicitud y Respuesta de ExpressJS-style pasen a la devolución de llamada onRequest().

Las funciones HTTP son síncronas, por lo que debes enviar una respuesta lo más rápido posible y aplazar el trabajo con Realtime Database. La función HTTP addMessage() transmite un valor de texto al extremo de HTTP y lo inserta en Realtime Database en la ruta /messages/:pushId/original que usa la app admin que se inicializó antes.

Implementa y ejecuta addMessage()

Para implementar y ejecutar la función addMessage(), sigue estos pasos:

  1. Ejecuta este comando para implementar las funciones:

    $ firebase deploy --only functions
    

    De forma predeterminada, Firebase CLI implementa todas las funciones dentro de index.js al mismo tiempo. Si ese archivo contiene varias funciones y solo necesitas implementar algunas de ellas, usa el argumento --only para realizar implementaciones parciales:

    $ firebase deploy --only functions:addMessage
    

    Después de realizar la implementación, Firebase CLI genera la URL de los extremos de la función HTTP, si los hay. En tu terminal, deberías ver una línea como la siguiente:

    Function URL (addMessage): https://us-central1-MY_PROJECT.cloudfunctions.net/addMessage
    

    En la configuración predeterminada, Firebase CLI busca el código fuente en la carpeta functions/. Agrega las siguientes líneas en firebase.json para especificar otra carpeta:

    "functions": {
      "source": "another-folder"
    }
    
  2. Agrega un parámetro de consulta de texto a la URL de addMessage() y ábrela en un navegador:

    https://us-central1-MY_PROJECT.cloudfunctions.net/addMessage?text=uppercaseme
    

    La función se ejecuta y redirecciona el navegador a Firebase console en la ubicación de la base de datos donde se almacena la string de texto. El valor de texto debería aparecer en la consola.

Después de implementar y ejecutar funciones, puedes ver registros en Firebase console.

Agrega la función makeUppercase()

Para la función makeUppercase(), agrega estas líneas a index.js:

// Listens for new messages added to /messages/:pushId/original and creates an
// uppercase version of the message to /messages/:pushId/uppercase
exports.makeUppercase = functions.database.ref('/messages/{pushId}/original')
    .onCreate((snapshot, context) => {
      // Grab the current value of what was written to the Realtime Database.
      const original = snapshot.val();
      console.log('Uppercasing', context.params.pushId, original);
      const uppercase = original.toUpperCase();
      // You must return a Promise when performing asynchronous tasks inside a Functions such as
      // writing to the Firebase Realtime Database.
      // Setting an "uppercase" sibling in the Realtime Database returns a Promise.
      return snapshot.ref.parent.child('uppercase').set(uppercase);
    });

La función makeUppercase() se ejecuta cuando se escribe en Realtime Database. La función ref(path) define la parte de la base de datos que se intenta detectar. Por motivos de rendimiento, debes ser lo más específico posible.

Las llaves, por ejemplo, {pushId}, encierran "parámetros", comodines que exponen las coincidencias de datos en la devolución de llamada.

Realtime Database activa la devolución de llamada onWrite() cada vez que se escriben o actualizan datos en la ruta de acceso especificada.

Las funciones controladas por eventos, como los eventos de Realtime Database, son asíncronas. La función de devolución de llamada debería mostrar null, un objeto o una Promesa. Si no se muestra nada, se agota el tiempo de espera de la función, se indica un error y se hace un nuevo intento. Consulta Síncrono, asíncrono y promesas.

Implementa y ejecuta makeUppercase()

Para completar el instructivo, implementa las funciones nuevamente y luego ejecuta addMessage() para activar makeUppercase().

  1. Ejecuta este comando para implementar las funciones:

    $ firebase deploy --only functions
    

    En la configuración predeterminada, Firebase CLI busca el código fuente en la carpeta functions/. Agrega las siguientes líneas en firebase.json para especificar otra carpeta:

    "functions": {
      "source": "another-folder"
    }
    

    Si encuentras errores de acceso como "No se pudo autorizar el acceso al proyecto", prueba revisar el alias de tu proyecto.

  2. Con la URL de addMessage() generada por la CLI, agrega un parámetro de consulta de texto y ábrelo en un navegador:

    https://us-central1-MY_PROJECT.cloudfunctions.net/addMessage?text=uppercasemetoo
    

    La función se ejecuta y redirecciona el navegador a Firebase console en la ubicación de la base de datos donde se almacena la string de texto. Este evento de escritura activa makeUppercase(), que escribe una versión de la string en mayúsculas.

Después de implementar y ejecutar funciones, puedes ver registros en Firebase console para Cloud Functions.

Revisa el código completo de la muestra

Aquí se muestra la versión completa de functions/index.js, que contiene las funciones addMessage() y makeUppercase(). Estas funciones te permiten pasarle un parámetro a un extremo HTTP que escribe un valor en Realtime Database, para luego transformarlo mediante el uso de mayúsculas en todos los caracteres de la string.

// The Cloud Functions for Firebase SDK to create Cloud Functions and setup triggers.
const functions = require('firebase-functions');

// The Firebase Admin SDK to access the Firebase Realtime Database.
const admin = require('firebase-admin');
admin.initializeApp();

// Take the text parameter passed to this HTTP endpoint and insert it into the
// Realtime Database under the path /messages/:pushId/original
exports.addMessage = functions.https.onRequest((req, res) => {
  // Grab the text parameter.
  const original = req.query.text;
  // Push the new message into the Realtime Database using the Firebase Admin SDK.
  return admin.database().ref('/messages').push({original: original}).then((snapshot) => {
    // Redirect with 303 SEE OTHER to the URL of the pushed object in the Firebase console.
    return res.redirect(303, snapshot.ref.toString());
  });
});

// Listens for new messages added to /messages/:pushId/original and creates an
// uppercase version of the message to /messages/:pushId/uppercase
exports.makeUppercase = functions.database.ref('/messages/{pushId}/original')
    .onCreate((snapshot, context) => {
      // Grab the current value of what was written to the Realtime Database.
      const original = snapshot.val();
      console.log('Uppercasing', context.params.pushId, original);
      const uppercase = original.toUpperCase();
      // You must return a Promise when performing asynchronous tasks inside a Functions such as
      // writing to the Firebase Realtime Database.
      // Setting an "uppercase" sibling in the Realtime Database returns a Promise.
      return snapshot.ref.parent.child('uppercase').set(uppercase);
    });

Próximos pasos

En esta documentación, podrás encontrar más información sobre los conceptos generales de Cloud Functions, así como guías sobre las funciones de escritura para controlar los tipos de evento compatibles con Cloud Functions.

Para obtener más información sobre Cloud Functions, puedes hacer lo siguiente:

Video instructivo

Mira videos instructivos para obtener más información sobre Cloud Functions. En este video, encontrarás una guía detallada sobre cómo comenzar con Cloud Functions, incluida la configuración de Node.js y de la CLI.

Enviar comentarios sobre…

¿Necesitas ayuda? Visita nuestra página de asistencia.