[[google-cloud-functions]] = Google Cloud Functions :page-aliases: adapters/gcp.adoc The Google Cloud Functions adapter enables Spring Cloud Function apps to run on the https://cloud.google.com/functions[Google Cloud Functions] serverless platform. You can either run the function locally using the open source https://github.com/GoogleCloudPlatform/functions-framework-java[Google Functions Framework for Java] or on GCP. [[project-dependencies]] == Project Dependencies Start by adding the `spring-cloud-function-adapter-gcp` dependency to your project. [source, xml] ---- org.springframework.cloud spring-cloud-function-adapter-gcp ... ---- In addition, add the `spring-boot-maven-plugin` which will build the JAR of the function to deploy. NOTE: Notice that we also reference `spring-cloud-function-adapter-gcp` as a dependency of the `spring-boot-maven-plugin`. This is necessary because it modifies the plugin to package your function in the correct JAR format for deployment on Google Cloud Functions. [source, xml] ---- org.springframework.boot spring-boot-maven-plugin target/deploy org.springframework.cloud spring-cloud-function-adapter-gcp ---- Finally, add the Maven plugin provided as part of the Google Functions Framework for Java. This allows you to test your functions locally via `mvn function:run`. NOTE: The function target should always be set to `org.springframework.cloud.function.adapter.gcp.GcfJarLauncher`; this is an adapter class which acts as the entry point to your Spring Cloud Function from the Google Cloud Functions platform. [source,xml] ---- com.google.cloud.functions function-maven-plugin 0.9.1 org.springframework.cloud.function.adapter.gcp.GcfJarLauncher 8080 ---- A full example of a working `pom.xml` can be found in the https://github.com/spring-cloud/spring-cloud-function/blob/master/spring-cloud-function-samples/function-sample-gcp-http/pom.xml[Spring Cloud Functions GCP sample]. [[http-functions]] == HTTP Functions Google Cloud Functions supports deploying https://cloud.google.com/functions/docs/writing/http[HTTP Functions], which are functions that are invoked by HTTP request. The sections below describe instructions for deploying a Spring Cloud Function as an HTTP Function. [[getting-started]] == Getting Started Let’s start with a simple Spring Cloud Function example: [source, java] ---- @SpringBootApplication public class CloudFunctionMain { public static void main(String[] args) { SpringApplication.run(CloudFunctionMain.class, args); } @Bean public Function uppercase() { return value -> value.toUpperCase(); } } ---- Specify your configuration main class in `resources/META-INF/MANIFEST.MF`. [source] ---- Main-Class: com.example.CloudFunctionMain ---- Then run the function locally. This is provided by the Google Cloud Functions `function-maven-plugin` described in the project dependencies section. ---- mvn function:run ---- Invoke the HTTP function: ---- curl http://localhost:8080/ -d "hello" ---- == Build & Deploy to GCP Start by packaging your application. ---- mvn package ---- If you added the custom `spring-boot-maven-plugin` plugin defined above, you should see the resulting JAR in `target/deploy` directory. This JAR is correctly formatted for deployment to Google Cloud Functions. Next, make sure that you have the https://cloud.google.com/sdk/install[Cloud SDK CLI] installed. From the project base directory run the following command to deploy. ---- gcloud functions deploy function-sample-gcp-http \ --entry-point org.springframework.cloud.function.adapter.gcp.GcfJarLauncher \ --runtime java11 \ --trigger-http \ --source target/deploy \ --memory 512MB ---- Invoke the HTTP function: ---- curl https://REGION-PROJECT_ID.cloudfunctions.net/function-sample-gcp-http -d "hello" ---- Setting custom HTTP statusCode: ---- Functions can specify a custom HTTP response code by setting the `FunctionInvoker.HTTP_STATUS_CODE` header. ---- [source, java] ---- @Bean public Function> function() { String payload = "hello"; Message message = MessageBuilder.withPayload(payload).setHeader(FunctionInvoker.HTTP_STATUS_CODE, 404).build(); return input -> message; }; ---- [[background-functions]] == Background Functions Google Cloud Functions also supports deploying https://cloud.google.com/functions/docs/writing/background[Background Functions] which are invoked indirectly in response to an event, such as a message on a https://cloud.google.com/pubsub[Cloud Pub/Sub] topic, a change in a https://cloud.google.com/storage[Cloud Storage] bucket, or a https://firebase.google.com/[Firebase] event. The `spring-cloud-function-adapter-gcp` allows for functions to be deployed as background functions as well. The sections below describe the process for writing a Cloud Pub/Sub topic background function. However, there are a number of different event types that can trigger a background function to execute which are not discussed here; these are described in the https://cloud.google.com/functions/docs/calling[Background Function triggers documentation]. == GCP Getting Started Let’s start with a simple Spring Cloud Function which will run as a GCF background function: [source, java] ---- @SpringBootApplication public class BackgroundFunctionMain { public static void main(String[] args) { SpringApplication.run(BackgroundFunctionMain.class, args); } @Bean public Consumer pubSubFunction() { return message -> System.out.println("The Pub/Sub message data: " + message.getData()); } } ---- In addition, create `PubSubMessage` class in the project with the below definition. This class represents the https://cloud.google.com/functions/docs/calling/pubsub#event_structure[Pub/Sub event structure] which gets passed to your function on a Pub/Sub topic event. [source, java] ---- public class PubSubMessage { private String data; private Map attributes; private String messageId; private String publishTime; public String getData() { return data; } public void setData(String data) { this.data = data; } public Map getAttributes() { return attributes; } public void setAttributes(Map attributes) { this.attributes = attributes; } public String getMessageId() { return messageId; } public void setMessageId(String messageId) { this.messageId = messageId; } public String getPublishTime() { return publishTime; } public void setPublishTime(String publishTime) { this.publishTime = publishTime; } } ---- Specify your configuration main class in `resources/META-INF/MANIFEST.MF`. [source] ---- Main-Class: com.example.BackgroundFunctionMain ---- Then run the function locally. This is provided by the Google Cloud Functions `function-maven-plugin` described in the project dependencies section. ---- mvn function:run ---- Invoke the HTTP function: ---- curl localhost:8080 -H "Content-Type: application/json" -d '{"data":"hello"}' ---- Verify that the function was invoked by viewing the logs. [[deploy-to-gcp]] == Deploy to GCP In order to deploy your background function to GCP, first package your application. ---- mvn package ---- If you added the custom `spring-boot-maven-plugin` plugin defined above, you should see the resulting JAR in `target/deploy` directory. This JAR is correctly formatted for deployment to Google Cloud Functions. Next, make sure that you have the https://cloud.google.com/sdk/install[Cloud SDK CLI] installed. From the project base directory run the following command to deploy. ---- gcloud functions deploy function-sample-gcp-background \ --entry-point org.springframework.cloud.function.adapter.gcp.GcfJarLauncher \ --runtime java11 \ --trigger-topic my-functions-topic \ --source target/deploy \ --memory 512MB ---- Google Cloud Function will now invoke the function every time a message is published to the topic specified by `--trigger-topic`. For a walkthrough on testing and verifying your background function, see the instructions for running the https://github.com/spring-cloud/spring-cloud-function/tree/master/spring-cloud-function-samples/function-sample-gcp-background/[GCF Background Function sample]. [[sample-functions]] == Sample Functions The project provides the following sample functions as reference: * The https://github.com/spring-cloud/spring-cloud-function/tree/master/spring-cloud-function-samples/function-sample-gcp-http/[function-sample-gcp-http] is an HTTP Function which you can test locally and try deploying. * The https://github.com/spring-cloud/spring-cloud-function/tree/master/spring-cloud-function-samples/function-sample-gcp-background/[function-sample-gcp-background] shows an example of a background function that is triggered by a message being published to a specified Pub/Sub topic.