Cloud Run Functions admite varios métodos para ejecutar las funciones fuera del entorno de implementación de destino. Esto es particularmente útil para el desarrollo iterativo y situaciones en las que quieres probar tu función antes de implementarla.
La capacidad de ejecutar las funciones sin implementarlas puede simplificar las pruebas locales, el cumplimiento de las restricciones de localidad de datos y las implementaciones de múltiples nubes:
Restricciones de localidad de datos: Prueba tu función de forma local sin acceder a los datos de producción para evitar incumplir las reglas de localidad de datos de tu organización.
Implementaciones en múltiples nubes: Las implementaciones de funciones en múltiples nubes tienen un patrón establecido para mitigar el riesgo de tiempo de inactividad en entornos críticos para la confiabilidad. Implementar funciones en entornos que no sean de Cloud Run reduce el riesgo de que tu aplicación experimente un tiempo de inactividad no planificado.
Desarrolla funciones de forma local con Functions Framework
Puedes desarrollar y probar funciones de forma local con Functions Framework. Desarrollar una función de forma local puede ayudarte a probar tu código sin tener que volver a compilar el contenedor de la función. Esto puede ahorrar tiempo y facilitar la prueba de tu función.
Cloud Run usa las bibliotecas de código abierto de Functions Framework para unir tus funciones implementadas en una aplicación HTTP persistente.
Functions Framework también puede ejecutarse en cualquier otra plataforma que admita el lenguaje en sí, como tu máquina local, servidores locales y Compute Engine.
Instala dependencias
En el directorio de la función, instala la biblioteca de Functions Framework para tu lenguaje:
Node.js
npm install --save-dev @google-cloud/functions-framework
Python
pip3 install functions-framework
Comienza a usarlo
go install github.com/GoogleCloudPlatform/functions-framework-go/funcframework
Java
Maven
Si usas Maven, agrega lo siguiente al archivo pom.xml
:
Gradle
Si usas Gradle, agrega lo siguiente al archivo build.gradle
:
Consulta la biblioteca de Functions Framework para Java a fin de obtener más información.
C#
Los siguientes comandos usan plantillas .NET para crear una base de código nueva de función .NET con la biblioteca de Functions Framework de.NET como una dependencia:
# HTTP functions dotnet new gcf-http # CloudEvent functions dotnet new gcf-event
Ruby
En Ruby, Functions Framework debe agregarse a las dependencias de la función para implementarla en Cloud Run:
bundle add functions_framework
PHP
composer require google/cloud-functions-framework
Configura Functions Framework
Debes especificar el tipo y el nombre de la función que desees ejecutar antes de ejecutarla mediante Functions Framework. Estos atributos se pueden especificar como marcas de la interfaz de línea de comandos (CLI) o como variables de entorno.
Tipos de funciones compatibles
Functions Framework admite ambos tipos de funciones compatibles con Cloud Run Functions. Todos los entornos de ejecución de lenguajes admiten los tipos de firma http
y cloudevent
.
Tipo de función | Tipo de firma | Descripción | Entornos de ejecución compatibles |
---|---|---|---|
Funciones activadas por HTTP |
http
|
Funciones que reciben y responden solicitudes HTTP | Todos los entornos de ejecución |
Funciones de CloudEvent |
cloudevent
|
Formato de evento estándar de la industria | Todos los entornos de ejecución |
Especifica qué función se ejecutará
Debes especificar qué función dentro de tu código se debe ejecutar antes de ejecutar una función con Functions Framework. Para la mayoría de los lenguajes, puedes hacerlo si especificas el nombre del método de la función de destino como se muestra en las tablas a continuación. Ten en cuenta que existen excepciones a esta regla para los entornos de ejecución de Java y .NET.
Instrucciones por idioma
Consulta la siguiente tabla para obtener una lista de las opciones de configuración compatibles con cada lenguaje.
Node.js
Argumento de la CLI | Variable de entorno | Descripción |
---|---|---|
--port
|
PORT
|
El puerto en el que se deben escuchar las solicitudes (Predeterminado: 8080 )
|
--target
|
FUNCTION_TARGET
|
El nombre de la función export que se invocará (Predeterminado: function )
|
--signature-type
|
FUNCTION_SIGNATURE_TYPE
|
El tipo de firma que usa tu función. Puede ser http (predeterminado) o cloudevent .
|
Python
Argumento de la CLI | Variable de entorno | Descripción |
---|---|---|
--port
|
PORT
|
El puerto en el que se deben escuchar las solicitudes (Predeterminado: 8080 )
|
--target
|
FUNCTION_TARGET
|
El nombre de la función export que se invocará (Predeterminado: function )
|
--signature-type
|
FUNCTION_SIGNATURE_TYPE
|
El tipo de firma que usa tu función. Puede ser http (predeterminado) o cloudevent .
|
Go
Variable de entorno | Descripción |
---|---|
PORT
|
El puerto en el que se deben escuchar las solicitudes (Predeterminado: 8080 )
|
Java
Nombre del argumento | Variable de entorno | Descripción |
---|---|---|
run.port
|
PORT
|
El puerto en el que se deben escuchar las solicitudes (Predeterminado: 8080 )
|
run.functionTarget
|
FUNCTION_TARGET
|
El nombre de la función export que se invocará (Predeterminado: function )
|
C#
Argumento de la CLI | Variable de entorno | Descripción |
---|---|---|
--port
|
PORT
|
El puerto en el que se deben escuchar las solicitudes (Predeterminado: 8080 )
|
--target (o solo el argumento)
|
FUNCTION_TARGET
|
El classname de la función que se invocará (Predeterminado: function )
|
Ruby
Argumento de la CLI | Variable de entorno | Descripción |
---|---|---|
--port
|
PORT
|
El puerto en el que se deben escuchar las solicitudes (Predeterminado: 8080 )
|
--target
|
FUNCTION_TARGET
|
El nombre de la función export que se invocará (Predeterminado: function )
|
PHP
Variable de entorno | Descripción |
---|---|
FUNCTION_TARGET
|
El nombre de la función que se invocará (Predeterminado: function )
|
FUNCTION_SIGNATURE_TYPE
|
El tipo de firma que usa tu función. Puede ser http (predeterminado) o cloudevent .
|
Sigue estas instrucciones para configurar y ejecutar Functions Framework:
Node.js
Functions Framework para Node.js te permite especificar el nombre y el tipo de firma de tu función como argumentos de línea de comandos o variables de entorno.
También puedes especificar estos valores en el archivo de compilación package.json
si agregas una secuencia de comandos start
con los argumentos de la CLI requeridos, como se muestra en el siguiente ejemplo.
"scripts": { "start": "npx functions-framework --target=YOUR_FUNCTION_NAME [--signature-type=YOUR_SIGNATURE_TYPE]" }
Lo mismo se puede hacer con las variables de entorno:
"scripts": { "start": "FUNCTION_TARGET=YOUR_FUNCTION_NAME FUNCTION_SIGNATURE_TYPE=YOUR_SIGNATURE_TYPE npx functions-framework" }
Reemplaza YOUR_FUNCTION_NAME por el nombre del método y YOUR_SIGNATURE_TYPE por el tipo de firma de la función, si corresponde, como se muestra en los tipos de funciones admitidos.
Python
Functions Framework para Python te permite especificar el nombre y el tipo de firma de la función como argumentos de línea de comandos o variables de entorno. Los argumentos de línea de comandos deben especificarse cuando ejecutas el framework.
Go
Functions Framework de Go usa funcframework.RegisterHTTPFunctionContext
para especificar el destino y el tipo de firma de la función.
Java
Functions Framework para Java acepta datos de configuración de tres fuentes diferentes en el siguiente orden de prioridad (del más específico al menos específico):
- Argumentos de la línea de comandos
- Archivos de compilación
- Variables de entorno
Argumentos de la línea de comandos
Maven
Para especificar la función que deseas ejecutar, agrega la siguiente marca de la interfaz de línea de comandos (CLI) a los comandos mvn
:
-Drun.functionTarget=YOUR_FUNCTION_NAME
También puedes especificar el puerto de destino si agregas la siguiente marca de la CLI de forma similar:
-Drun.port=12345
Gradle
Los marcas de la CLI de Gradle son casi idénticas a las de Maven. El único cambio que realiza Gradle es intercambiar la -D
inicial en cada marca por una -P
, como se muestra en el siguiente ejemplo:
# Maven version -Drun.functionTarget=... # Gradle version -Prun.functionTarget=...
Archivos de compilación
También puedes especificar la función que desees ejecutar en el archivo de compilación del proyecto. Si bien Maven y Gradle tienen marcas similares de la CLI, sus cláusulas de archivo de compilación difieren de manera significativa.
Maven
Los archivos de compilación de Maven se denominan pom.xml
. Agrega la siguiente cláusula a este archivo para especificar una función de destino:
Reemplaza <functionTarget>
por el nombre de clase de tu función. Por ejemplo, una función en el paquete functions
con el nombre de clase HelloCloudFunctions
tendría un nombre de clase functions.HelloCloudFunctions
. Esto está relacionado con el archivo de compilación superior, ya sea pom.xml
o build.gradle
.
Gradle
Los archivos de compilación de Gradle se denominan build.gradle
. Agrega la siguiente cláusula a este archivo para especificar una función de destino:
C#
Si creas tu proyecto con dotnet new
y una de las plantillas especificadas antes, Functions Framework para .NET detectará de forma automática la función.
Si tu proyecto contiene varias funciones, consulta la sección Ejecuta el framework a fin de obtener información para ejecutar una función específica.
Ruby
Functions Framework para Ruby te permite especificar el nombre y el tipo de firma de la función como argumentos de línea de comandos o variables de entorno. Los argumentos de línea de comandos deben especificarse cuando ejecutas el framework.
PHP
Functions Framework de PHP te permite especificar variables de entorno como argumentos de línea de comandos.
También puedes especificar estos valores en el archivo de compilación composer.json
si agregas una secuencia de comandos start
como se muestra en el siguiente ejemplo.
"scripts": { "start": [ "Composer\\Config::disableProcessTimeout", "FUNCTION_TARGET=YOUR_FUNCTION_NAME php -S localhost:${PORT:-8080} vendor/bin/router.php" ]. }
Reemplaza YOUR_FUNCTION_NAME por el nombre de tu función y YOUR_SIGNATURE_TYPE (si corresponde; no se incluye en el ejemplo que se muestra aquí).
Ejecuta tu función
Usa el siguiente comando para ejecutar la función con Functions Framework.
De forma predeterminada, se podrá acceder a la función en localhost:8080
, a menos que especifiques de forma explícita un valor PORT
.
Node.js
npm start
Python
Usa los argumentos de línea de comandos:
functions-framework --target=YOUR_FUNCTION_NAME
Usa variables de entorno
FUNCTION_TARGET=YOUR_FUNCTION_NAME functions-framework
Reemplaza YOUR_FUNCTION_NAME por el nombre del método de la función.
Go
Primero, crea un archivo cmd/main.go
como se describe en el sitio Functions Framework para Go.
cd cmd go build ./cmd
Usa variables de entorno
cd cmd go build PORT=8080 ./cmd
Java
Maven
Usa el siguiente comando para ejecutar una función especificada en pom.xml
:
mvn function:run
Usa el siguiente comando para ejecutar una función especificada en un argumento de línea de comandos:
mvn function:run -Drun.functionTarget=YOUR_FUNCTION_NAME
Usa el siguiente comando para ejecutar una función especificada como una variable de entorno:
FUNCTION_TARGET=YOUR_FUNCTION_NAME mvn function:run
Reemplaza YOUR_FUNCTION_NAME por el nombre de clase de la función.
Gradle
Usa el siguiente comando para ejecutar una función especificada en build.gradle
:
./gradlew runFunction
Usa el siguiente comando para ejecutar una función especificada en un argumento de línea de comandos:
./gradlew runFunction -Prun.functionTarget=YOUR_FUNCTION_NAME
Usa el siguiente comando para ejecutar una función especificada como una variable de entorno:
FUNCTION_TARGET=YOUR_FUNCTION_NAME ./gradlew runFunction
Reemplaza YOUR_FUNCTION_NAME por el nombre de clase de la función.
C#
Usa el siguiente comando para ejecutar la función cuando esté presente solo una función en el proyecto .NET actual Ten en cuenta que esta es la estructura predeterminada para los proyectos creados con plantillas.
dotnet run
Si tu proyecto .NET contiene varias funciones, usa el siguiente comando para ejecutar una función específica. Reemplaza YOUR_FUNCTION_CLASSNAME por el nombre de clase de la función, incluido el espacio de nombres.
dotnet run YOUR_FUNCTION_CLASSNAME
Si deseas ejecutar varias funciones de forma simultánea, deberás ejecutar varias instancias de Functions Framework. Para evitar conflictos entre las instancias de framework en ejecución, cada instancia debe usar un valor PORT
diferente. En el siguiente comando, se muestra cómo ejecutar una función con un valor PORT
de 8080
.
Usa los argumentos de línea de comandos:
dotnet run --target YOUR_FUNCTION_CLASSNAME --port 8080
Usa variables de entorno
FUNCTION_TARGET=YOUR_FUNCTION_CLASSNAME PORT=8080 dotnet run
Ruby
Usa los argumentos de línea de comandos:
bundle exec functions-framework-ruby --target YOUR_FUNCTION_NAME
Usa variables de entorno
FUNCTION_TARGET=YOUR_FUNCTION_NAME bundle exec functions-framework-ruby
Reemplaza YOUR_FUNCTION_NAME por el nombre del método de la función.
PHP
export FUNCTION_TARGET=YOUR_FUNCTION_NAME php -S localhost:8080 vendor/bin/router.php
Reemplaza YOUR_FUNCTION_NAME por el nombre de la función.
Llama a tu función que se ejecuta de forma local
En los ejercicios de esta sección, se supone que configuraste una función que se ejecuta de forma local en localhost
con Functions Framework.
Puedes activar funciones que se ejecuten de forma local si envías solicitudes HTTP enrutadas a través de un proceso de entrega local.
Funciones de HTTP
Cuando pruebas tu función de HTTP desde tu entorno de desarrollo, esta suele
escuchar solicitudes en localhost:8080
. Solo se puede acceder a esta interfaz desde la máquina o VM en la que se ejecuta tu función; las solicitudes enviadas desde cualquier otro sistema no pueden acceder a la interfaz. Por este motivo, debes emitir la solicitud HTTP desde el
mismo sistema en el que se ejecuta tu función. En los siguientes ejemplos, si tu función escucha en un puerto distinto de 8080, reemplaza 8080 en el ejemplo por el número de puerto de tu función.
Prueba funciones de HTTP con Cloud Shell
Si usas Cloud Shell para compilar y probar tu función, inicia tu función de forma local en la ventana de la terminal de Cloud Shell y, luego, emite la solicitud del activador HTTP desde un navegador o una instancia curl
de la siguiente manera:
Navegador
Haz clic en el ícono en la barra de herramientas de Cloud Shell y elige puerto 8080 o Cambiar puerto para elegir otro. De este modo, se abrirá una ventana del navegador en el sistema correcto y
se emitirá una solicitud GET al puerto indicado.
Curl
Para controlar el formato de tu solicitud HTTP o ver la respuesta sin formato,
usa curl
:
- Haz clic en el ícono + en la barra de menú de Cloud Shell para abrir una ventana de terminal nueva en el mismo sistema en el que se ejecuta tu función.
Desde esa ventana, ejecuta el comando
curl
para activar la función. Por ejemplo:curl localhost:8080
Prueba funciones de HTTP en tu servidor de escritorio
Si compilas y ejecutas tu función en tu sistema de escritorio local, primero
iníciala de forma local y, luego, emite la solicitud del activador HTTP desde un navegador
o una instancia curl
de la siguiente manera:
Navegador
Abre una nueva ventana o pestaña del navegador y escribe http://localhost:8080
en la
barra de direcciones del navegador. De este modo, se abrirá una ventana del navegador en localhost:8080
en tu
servidor de escritorio para activar la función.
Curl
Abre una nueva ventana de terminal en el escritorio local y, luego, ejecuta el comando curl
en esa ventana para activar la función. Por ejemplo:
curl localhost:8080
Esto ejecuta el comando curl
especificado para activar la función y muestra
la respuesta sin formato.
Funciones de CloudEvent
Puedes enviar eventos de muestra a las funciones de CloudEvent mediante curl
. En las siguientes solicitudes curl
, se muestra cómo enviar eventos de muestra de
Pub/Sub y
Cloud Storage a una
función de CloudEvent que se ejecuta en localhost:8080
.
Pub/Sub
curl localhost:8080 \ -X POST \ -H "Content-Type: application/json" \ -H "ce-id: 123451234512345" \ -H "ce-specversion: 1.0" \ -H "ce-time: 2020-01-02T12:34:56.789Z" \ -H "ce-type: google.cloud.pubsub.topic.v1.messagePublished" \ -H "ce-source: //pubsub.googleapis.com/projects/MY-PROJECT/topics/MY-TOPIC" \ -d '{ "message": { "data": "d29ybGQ=", "attributes": { "attr1":"attr1-value" } }, "subscription": "projects/MY-PROJECT/subscriptions/MY-SUB" }'
Cloud Storage
curl localhost:8080 \ -X POST \ -H "Content-Type: application/json" \ -H "ce-id: 123451234512345" \ -H "ce-specversion: 1.0" \ -H "ce-time: 2020-01-02T12:34:56.789Z" \ -H "ce-type: google.cloud.storage.object.v1.finalized" \ -H "ce-source: //storage.googleapis.com/projects/_/buckets/MY-BUCKET-NAME" \ -H "ce-subject: objects/MY_FILE.txt" \ -d '{ "bucket": "MY_BUCKET", "contentType": "text/plain", "kind": "storage#object", "md5Hash": "...", "metageneration": "1", "name": "MY_FILE.txt", "size": "352", "storageClass": "MULTI_REGIONAL", "timeCreated": "2020-04-23T07:38:57.230Z", "timeStorageClassUpdated": "2020-04-23T07:38:57.230Z", "updated": "2020-04-23T07:38:57.230Z" }'