编辑此页面

Funqy

Quarkus Funqy 是 Quarkus 的无服务器策略的一部分,旨在提供一个可移植的 Java API,用于编写可部署到各种 FaaS 环境(如 AWS Lambda、Azure Functions、Google Cloud Functions、Knative 和 Knative Events(Cloud Events))的函数。它也可以作为独立服务使用。

由于 Funqy 是一个跨越多种不同云/函数提供商和协议的抽象,因此它必须是一个非常简单的 API,因此可能不具备您在其他远程抽象中习惯的所有功能。一个不错的影响是 Funqy 尽可能优化和小型化。这意味着,由于 Funqy 在灵活性上做出了一点牺牲,您将获得一个几乎没有开销的框架。

Funqy 基础知识

Funqy API 很简单。用 @Funq 注释一个方法。此方法只能有一个可选的输入参数,并且可以返回响应,也可以不返回响应。

import io.quarkus.funqy.Funq;

public class GreetingFunction {
    @Funq
    public String greet(String name) {
       return "Hello " + name;
    }
}

Java 类也可以用作输入和输出,并且必须遵循 Java bean 约定并具有默认构造函数。声明为参数或返回类型的 Java 类型是 Funqy 运行时期望的类型。Funqy 在构建时进行类型内省以加快启动速度,因此运行时 Funqy 编组层不会注意到任何派生类型。

这是一个使用 POJO 作为输入和输出类型的示例。

public class GreetingFunction {
    public static class Friend {
        String name;

        public String getName() { return name; }
        public void setName(String name) { this.name = name; }
    }

    public static class Greeting {
        String msg;

        public Greeting() {}
        public Greeting(String msg) { this.msg = msg }

        public String getMessage() { return msg; }
        public void setMessage(String msg) { this.msg = msg; }
    }

    @Funq
    public Greeting greet(Friend friend) {
       return new Greeting("Hello " + friend.getName());
    }
}

异步响应式类型

Funqy 支持 SmallRye MutinyUni 响应式类型作为返回类型。唯一的要求是 Uni 必须填写泛型类型。

import io.quarkus.funqy.Funq;
import io.smallrye.mutiny.Uni;

public class GreetingFunction {

    @Funq
    public Uni<Greeting> reactiveGreeting(String name) {
       ...
    }
}

函数名称

函数名默认为方法名,且区分大小写。如果您希望您的函数以不同的名称引用,请如下参数化 @Funq 注释

import io.quarkus.funqy.Funq;

public class GreetingFunction {

    @Funq("HelloWorld")
    public String greet(String name) {
       return "Hello " + name;
    }
}

Funqy DI

每个 Funqy Java 类都是一个 Quarkus Arc 组件,并支持通过 CDI 或 Spring DI 进行依赖注入。Spring DI 要求在构建中包含 quarkus-spring-di 依赖项。

Funqy 类的默认对象生命周期为 @Dependent

import io.quarkus.funqy.Funq;

import jakarta.inject.Inject;
import jakarta.enterprise.context.ApplicationScoped;

@ApplicationScoped
public class GreetingFunction {

    @Inject
    GreetingService service;

    @Funq
    public Greeting greet(Friend friend) {
        Greeting greeting = new Greeting();
        greeting.setMessage(service.greet(friend.getName()));
        return greeting;
    }
}

上下文注入

Funqy API 通常不允许您注入或使用特定于协议(例如 HTTP)或函数 API(例如 AWS Lambda)的抽象。不过,也有例外,您可能能够注入特定于您正在部署的环境的上下文信息。

我们不建议注入特定于运行时的上下文信息。请保持您的函数可移植。

上下文信息通过 @Context 注释注入,该注释可用于函数参数或类字段。一个很好的例子是我们 Funqy Knative Cloud Events 集成随附的 io.quarkus.funqy.knative.events.CloudEvent 接口。

import io.quarkus.funqy.Funq;
import io.quarkus.funqy.Context;
import io.quarkus.funqy.knative.events.CloudEvent;

public class GreetingFunction {

    @Funq
    public Greeting greet(Friend friend, @Context CloudEvent eventInfo) {
        System.out.println("Received greeting request from: " eventInfo.getSource());

        Greeting greeting = new Greeting();
        greeting.setMessage("Hello " + friend.getName()));
        return greeting;
    }
}

我应该使用 Funqy 吗?

在过去十年中,HTTP 上的 REST 已成为编写服务的非常流行的方式。虽然 Funqy 具有 HTTP 绑定,但它并不能替代 REST。由于 Funqy 必须跨各种协议和函数云平台工作,因此它非常简约且受限制。例如,如果您使用 Funqy,您将无法链接(考虑 URIs)到您的函数输出的数据。您还将失去利用诸如 cache-control 和条件 GET 等出色 HTTP 功能的能力。许多开发人员对此会没事的,因为许多人不会使用这些 REST/HTTP 功能或样式。您必须决定您属于哪个阵营。Quarkus 通过 Jakarta REST、Spring MVC、Vert.x Web 和 Servlet 支持与各种云/函数提供商的 REST 集成,但使用该方法也有一些缺点。例如,如果您想使用 AWS Lambda 进行 HTTP,这需要您使用 AWS API Gateway,这可能会减慢部署和冷启动时间,甚至花费更多。

Funqy 的目的是允许您编写跨提供商的函数,这样您就可以摆脱您当前的函数提供商,例如,如果他们开始向您收取更高的服务费。您可能不想使用 Funqy 的另一个原因是,如果您需要访问目标函数环境的特定 API。例如,开发人员通常希望在 Lambda 上访问 AWS Context。在这种情况下,我们建议他们最好使用 Quarkus AWS Lambda 集成。

相关内容