1. Introduction
Overview
Cloud Run functions is a new way to deploy workloads using the familiar GCF eventing paradigms and function signature. Instead of using our opinionated build process and deployment configurations, Cloud Run functions gives you direct control over the underlying Service created on Cloud Run.
With Cloud Run functions, we provide the simple UX of Cloud Run source deploy, giving developers complete control over their workloads using Cloud Run configurations.
In this section, you'll learn how to deploy an event-driven function in Node. You'll deploy a function that is triggered whenever an object is finalized in a Google Cloud Storage bucket.
This codelab uses nodejs samples in the examples below. However, you can use the Cloud Functions 2nd gen code samples in the language of your choice:
- Python function samples
- Nodejs function samples
- Go function samples
- Java function samples
- PHP function samples
- Ruby function samples
- .NET function samples
What you'll learn
- How to deploy an event-driven Cloud Run function that is triggered whenever an object is uploaded to a GCS bucket
- How to create a service account with proper roles to receive an event from Cloud Storage and invoke the Cloud Run function
2. Setup environment variables and enable APIs
Update gcloud CLI
This codelab requires a recent version of the gcloud CLI installed. You can update the CLI by running
gcloud components update
Enable APIs
Before you can start using this codelab, there are several APIs you will need to enable. This codelab requires using the following APIs. You can enable those APIs by running the following command:
gcloud services enable run.googleapis.com \ cloudbuild.googleapis.com \ storage.googleapis.com \ artifactregistry.googleapis.com
Setup environment variables
You can set environment variables that will be used throughout this codelab.
PROJECT_ID=<YOUR_PROJECT_ID> REGION=<YOUR_REGION, e.g. us-central1> gcloud config set project $PROJECT_ID SERVICE_NAME=crf-event-codelab BUCKET_NAME=$PROJECT_ID-$SERVICE_NAME TRIGGER_NAME=$SERVICE_NAME-trigger
3. Create a Storage Bucket and a Service Account
Create a storage bucket
You can create a Cloud Storage bucket by running the following command:
gsutil mb -l us-central1 gs://$BUCKET_NAME
Create a service account
For this example, you'll create a service account with required EventArc permissions and Cloud Run invoker role to receive an event from Cloud Storage and invoke the Cloud Run function.
First, create the service account.
PROJECT_NUMBER=$(gcloud projects describe $PROJECT_ID --format='value(projectNumber)') SERVICE_ACCOUNT="cloud-run-functions" SERVICE_ACCOUNT_ADDRESS=$SERVICE_ACCOUNT@$PROJECT_ID.iam.gserviceaccount.com gcloud iam service-accounts create $SERVICE_ACCOUNT \ --display-name="Cloud Run functions Eventarc service account"
Next, grant the Eventarc Event Receiver role (roles/eventarc.eventReceiver) on the project to the service account associated with your Eventarc trigger so that the trigger can receive events from event providers.
gcloud projects add-iam-policy-binding $PROJECT_ID \ --member serviceAccount:$SERVICE_ACCOUNT_ADDRESS \ --role=roles/eventarc.eventReceiver
Then, grant the service account the Cloud Run invoker role so that it can invoke the function.
gcloud projects add-iam-policy-binding $PROJECT_ID \ --member serviceAccount:$SERVICE_ACCOUNT_ADDRESS \ --role=roles/run.invoker
4. Create and deploy the function
First, create a directory for the source code and cd into that directory.
mkdir ../$SERVICE_NAME && cd $_
Then, create a package.json
file with the following content:
{ "dependencies": { "@google-cloud/functions-framework": "^3.0.0" } }
Next, create an index.js
file with the following content:
const functions = require("@google-cloud/functions-framework"); // Register a CloudEvent callback with the Functions Framework that will // be triggered by Cloud Storage. functions.cloudEvent("helloGCS", (cloudEvent) => { console.log(`Event ID: ${cloudEvent.id}`); console.log(`Event Type: ${cloudEvent.type}`); const file = cloudEvent.data; console.log(`Bucket: ${file.bucket}`); console.log(`File: ${file.name}`); console.log(`Metageneration: ${file.metageneration}`); console.log(`Created: ${file.timeCreated}`); console.log(`Updated: ${file.updated}`); });
Now you can deploy the Cloud Run function by running the following command:
gcloud beta run deploy $SERVICE_NAME \ --source . \ --function helloGCS \ --region $REGION \ --no-allow-unauthenticated
Please note the following:
- the –source flag is used to tell Cloud Run to build the function into a runnable container based service
- the –function flag (new) is used to set the entrypoint of the new service to be the function signature you want to be invoked
- (optional) the –no-allow-unauthenticated to prevent your function from being publicly invokable
You can view your new service crf-nodejs-event
by running the following command:
gcloud beta run services describe $SERVICE_NAME
5. Create the event
We can create an Eventarc trigger to send messages to our function every time an object is finalized in Google Cloud Storage:
BUCKET_REGION=$REGION gcloud eventarc triggers create $TRIGGER_NAME \ --location=$REGION \ --destination-run-service=crf-nodejs-event \ --destination-run-region=$BUCKET_REGION \ --event-filters="type=google.cloud.storage.object.v1.finalized" \ --event-filters="bucket=$BUCKET_NAME" \ --service-account=$SERVICE_ACCOUNT_ADDRESS
Please note the following:
- gcs-function-trigger is the name of the trigger
- crf-nodejs-event is the name of the Cloud Run service where our function is deployed
- for the –event-filters flag, do not use the gs:// prefix in your bucket name.
A detailed tutorial of setting up Trigger service from Cloud Storage using Eventarc can be found in the Cloud Run documentation here: https://cloud.google.com/run/docs/tutorials/eventarc
6. Test the Function
When the deployment is complete, you will see the service URL. To invoke the function, you need to send an authenticated request with your identity token or the identity token of a principle that has the Cloud Run Invoker role, as shown below:
# get the Service URL SERVICE_URL="$(gcloud run services describe crf-nodejs-event --region us-central1 --format 'value(status.url)')" # invoke the service curl -H "Authorization: bearer $(gcloud auth print-identity-token)" -X GET $SERVICE_URL
With our function deployed and a trigger created, we are now ready to invoke the function.
Create a file and upload it to your Cloud Storage bucket. You can do this through the Cloud Console web interface, or using the gsutil CLI tool, e.g.
echo "hello world" > test.txt gsutil cp test gs://$BUCKET_NAME
When the file is successfully uploaded, an event will be generated and your function will print some basic information about the object e.g. the filename. You can find this output in the log entries for the function in the Cloud Console. Alternatively, you can query for this output using the gcloud CLI:
gcloud logging read "resource.labels.service_name=crf-nodejs-event AND textPayload: File" --format=json
and you should see the following output
"textPayload": "File: test.txt"
7. Congratulations!
Congratulations for completing the codelab!
We recommend reviewing the documentation for Cloud Run functions
What we've covered
- How to deploy an event-driven Cloud Run function that is triggered whenever an object is uploaded to a GCS bucket
- How to create a service account with proper roles to receive an event from Cloud Storage and invoke the Cloud Run function
8. Clean up
To avoid inadvertent charges, (for example, if this Cloud Run servcie is inadvertently invoked more times than your monthly Cloud Run invokement allocation in the free tier), you can either delete the Cloud Run service or delete the project you created in Step 2.
To delete the Cloud Run services, go to the Cloud Run Cloud Console at https://console.cloud.google.com/run/ and delete the crf-event-codelab
service you created in this codelab.
If you choose to delete the entire project, you can go to https://console.cloud.google.com/cloud-resource-manager, select the project you created in Step 2, and choose Delete. If you delete the project, you'll need to change projects in your Cloud SDK. You can view the list of all available projects by running gcloud projects list
.