You can use Java handlers to respond to received events and execute corresponding business logic. This topic describes concepts and features of Java handlers and provides examples.
If you want to use HTTP triggers or custom domain names to access functions, obtain request struct before you define HTTP responses. For more information, see Use an HTTP trigger to invoke a function.
What is a handler?
A handler of a function in FC is used to process requests in function code. When a function is invoked, Function Compute uses the handler that you configure to process requests.
You can configure a handler for a function by specifying the Handler parameter in the Function Compute console. Handlers of Java functions follow the [Package name].[Class name]::[Method name]
format. For example, if the name of your package is example, the class type is HelloFC, and the method is handleRequest, the handler can be configured as example.HelloFC::handleRequest
.
Configurations of handlers must conform to the configuration specifications of Function Compute. The configuration specifications vary based on the handler type.
Handler interfaces
If you use Java for programming, you must implement the interface class provided by Function Compute. The fc-java-core library defines the following interfaces for handlers:
Uses streams to receive the input
event
data and returns responses. You must read input data from input streams and then write execution results to output streams.Uses a generic type to receive the input
event
and returns responses. You can customize types of input and output data of a handler. Both the input and output data must be of the Plain Old Java Object (POJO) type.
StreamRequestHandler
The following sample code shows a simple StreamRequestHandler:
package example;
import com.aliyun.fc.runtime.Context;
import com.aliyun.fc.runtime.StreamRequestHandler;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
public class HelloFC implements StreamRequestHandler {
@Override
public void handleRequest(InputStream inputStream, OutputStream outputStream, Context context) throws IOException {
outputStream.write(new String("hello world").getBytes());
}
}
Package names and class names
Java is different from other programming languages in execution methods based on packages. In the preceding sample code, the handler is
example.HelloFC::handleRequest
.example
indicates the package name,HelloFC
indicates the class name, andhandleRequest
indicates the class method.NoteThe package name and class name can be customized. However, the names must be consistent with the value of the Handler parameter in the function configurations. For more information about how to configure Handler, see Create an event function.
Implemented interfaces
Your code must implement the interfaces that are predefined by Function Compute. In the preceding sample code,
StreamRequestHandler
is implemented. The inputStream parameter is the data passed into Function Compute when you invoke a function. The outputStream parameter is used to return execution results of the function.Context
The Context parameter contains the runtime information of a function, such as the request ID and the temporary AccessKey pair. The type is
com.aliyun.fc.runtime.Context
. For more information, see Context.Return value
A function that implements
StreamRequestHandler
returns execution results by using theoutputStream
parameter.Interface libraries
The dependency of the
com.aliyun.fc.runtime
package can be referenced in thepom.xml
file in the following sample code:<dependency> <groupId>com.aliyun.fc.runtime</groupId> <artifactId>fc-java-core</artifactId> <version>1.4.1</version> </dependency>
You can visit the Maven repository to obtain the latest version of the
fc-java-core
package.
Before you create a function, you must compress the code and its dependency fc-java-core
into a JAR file. For more information about how to compress code and dependencies, see Compile and deploy code packages.
PojoRequestHandler
The following sample code shows a simple PojoRequestHandler. The SimpleRequest object must support JSON serialization. For example, you can use POJO.
// HelloFC.java
package example;
import com.aliyun.fc.runtime.Context;
import com.aliyun.fc.runtime.PojoRequestHandler;
public class HelloFC implements PojoRequestHandler<SimpleRequest, SimpleResponse> {
@Override
public SimpleResponse handleRequest(SimpleRequest request, Context context) {
String message = "Hello, " + request.getFirstName() + " " + request.getLastName();
return new SimpleResponse(message);
}
}
// SimpleRequest.java
package example;
public class SimpleRequest {
String firstName;
String lastName;
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public SimpleRequest() {}
public SimpleRequest(String firstName, String lastName) {
this.firstName = firstName;
this.lastName = lastName;
}
}
// SimpleResponse.java
package example;
public class SimpleResponse {
String message;
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
public SimpleResponse() {}
public SimpleResponse(String message) {
this.message = message;
}
}
The following sample code describes the input event parameter:
{
"firstName": "FC",
"lastName": "aliyun"
}
Example: Use an HTTP trigger to invoke a function
Sample code
In the preceding sample code, HTTPTriggerEvent.java declares the request format of the HTTP trigger, and HTTPTriggerResponse.java declares the response format of the HTTP trigger. For more information about the formats of requests and responses of HTTP triggers, see Use an HTTP trigger to invoke a function.
App.java defines the entry class of the function.
In this example, in addition to the fc-java-core library, the jackson and lombok libraries must be introduced. You can add this dependency in the Maven settings file pom.xml
.
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.16.1</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.30</version>
</dependency>
Before you start
Use the preceding sample code to create a function in a Java runtime and create an HTTP trigger. For more information, see Create an event function and Configure an HTTP trigger that invokes a function with HTTP requests.
Procedure
Log on to the Function Compute console. In the left-side navigation pane, click Functions.
In the top navigation bar, select a region. On the Functions page, click the function that you want to manage.
On the function details page, click the Triggers tab to obtain the public endpoint of the HTTP trigger.
Run the following command in curl to invoke the function:
curl -i "https://dev-jav-test-fc-luiqas****.cn-shanghai.fcapp.run" -d 'hello fc3.0'
In the preceding command,
https://dev-jav-test-fc-luiqas****.cn-shanghai.fcapp.run
is the public endpoint of the HTTP trigger.The following result is returned:
HTTP/1.1 200 OK Content-Disposition: attachment Content-Length: 11 Content-Type: application/json X-Fc-Request-Id: 1-652503f2-afbfd2b1dc4dd0fcb0230959 Date: Tue, 10 Oct 2023 07:57:38 GMT hello fc3.0%
ImportantIf the Authentication Method parameter of the HTTP trigger is set to No Authentication, you can use Postman or curl to invoke the function. For more information, see Procedure.
If the Authentication Method parameter of the HTTP trigger is set to Signature Authentication or JWT Authentication, use the signature method or JWT authentication method to invoke the function. For more information, see Authentication.
Possible errors
This sample code can be called by using an HTTP trigger or a custom domain name. If you use an API operation but the configured test parameters do not comply with the request format requirements of HTTP triggers, an error is reported.
For example, the following response is returned if you invoke the function by clicking Test Function in the Function Compute console after you configure the request parameters as "Hello, FC!"
.
{
"errorType": "com.fasterxml.jackson.databind.exc.MismatchedInputException",
"errorMessage": "Cannot construct instance of `example.HTTPTriggerEvent` (although at least one Creator exists): no String-argument constructor/factory method to deserialize from String value ('Hello, FC!')\n at [Source: (byte[])\"\"Hello, FC!\"\"; line: 1, column: 1]",
"stackTrace": [
"com.fasterxml.jackson.databind.exc.MismatchedInputException.from(MismatchedInputException.java:63)",
"com.fasterxml.jackson.databind.DeserializationContext.reportInputMismatch(DeserializationContext.java:1588)",
"com.fasterxml.jackson.databind.DeserializationContext.handleMissingInstantiator(DeserializationContext.java:1213)",
"com.fasterxml.jackson.databind.deser.std.StdDeserializer._deserializeFromString(StdDeserializer.java:311)",
"com.fasterxml.jackson.databind.deser.BeanDeserializerBase.deserializeFromString(BeanDeserializerBase.java:1495)",
"com.fasterxml.jackson.databind.deser.BeanDeserializer._deserializeOther(BeanDeserializer.java:207)",
"com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:197)",
"com.fasterxml.jackson.databind.deser.DefaultDeserializationContext.readRootValue(DefaultDeserializationContext.java:322)",
"com.fasterxml.jackson.databind.ObjectMapper._readMapAndClose(ObjectMapper.java:4593)",
"com.fasterxml.jackson.databind.ObjectMapper.readValue(ObjectMapper.java:3643)"
]
}
Sample programs
Function Compute official libraries contain sample programs that use various types of handlers and interfaces. Each sample program contains methods for easy compilation and deployment. The following items provide examples:
java11-blank-stream-event: uses event callbacks in the stream format.
java11-blank-pojo-event: uses event callbacks in the POJO format.