JavaCallout 政策

本页面适用于 ApigeeApigee Hybrid

查看 Apigee Edge 文档。

政策图标

内容

让您可使用 Java 实施 Apigee 政策未开箱包括的自定义行为。在 Java 代码中,您可以访问代理流中的消息属性(标头、查询参数、内容)和流变量。如果您刚开始使用此政策,请参阅如何创建 Java 标注

支持的 Java 版本包括:Oracle JDK 11 和 OpenJDK 11

此政策是一项可扩展政策,使用此政策可能会影响费用或使用情况,具体取决于您的 Apigee 许可。如需了解政策类型和使用情况影响,请参阅政策类型

时间

如需了解准则,请参阅如何创建 Java 标注中的“我应在何时使用 Java 标注?”。

简介

通过 Java 标注政策,您可以获取和设置流变量、执行自定义逻辑并执行错误处理、从请求或响应中提取数据,等等。该政策让您可实施任何其他标准 Apigee 政策未涵盖的自定义行为。

您可以使用所需的任何软件包 JAR 文件打包 Java 应用。请注意,您可以使用 Java 标注执行的操作存在一些限制。下文的限制部分中列出了这些限制。

示例

简单示例

如何创建 JavaCallout

在 Java 代码中检索属性

通过此政策的 <Property> 元素,您可以指定可在 Java 代码中在运行时检索的名称/值对。如需查看使用属性的有效示例,请参阅如何在 Java 标注中使用属性

使用 <Property> 元素的 name 特性指定可用于从 Java 代码访问属性的名称。<Property> 元素的值(起始标记和结束标记之间的值)是 Java 代码将接收的值。值必须是字符串;您无法引用流变量来获取值。

  • 配置属性。在这里,属性值为变量名称 response.status.code
    <JavaCallout async="false" continueOnError="false" enabled="true" name="JavaCallout">
        <DisplayName>JavaCallout</DisplayName>
        <ClassName>com.example.mypolicy.MyJavaCallout</ClassName>
        <ResourceURL>java://MyJavaCallout.jar</ResourceURL>
        <Properties>
            <Property name="source">response.status.code</Property>
        </Properties>
    </Javascript>
    
  • 在 Java 代码中,在 Execution 类实施上实施以下构造函数,如下所示:
    public class MyJavaCallout implements Execution{
        public MyJavaCallout(Map<string, string> props){
    
                // Extract property values from map.
        }
        ...
    }
    

在 Java 代码中设置流变量

如需清楚了解如何在 Java 代码的消息上下文(流变量)中设置变量,请参阅这篇 Apigee 社区博文


元素参考

元素参考描述了 JavaCallout 政策的元素和特性。

<JavaCallout name="MyJavaCalloutPolicy">
   <ClassName>com.example.mypolicy.MyJavaCallout</ClassName>
   <ResourceURL>java://MyJavaCallout.jar</ResourceURL>
</JavaCallout>

<JavaCallout> 特性

<JavaCallout name="MyJavaCalloutPolicy" enabled="true" continueOnError="false" async="false" >

下表介绍了所有政策父元素通用的特性:

特性 说明 默认 状态
name

政策的内部名称。name 特性的值可以包含字母、数字、空格、连字符、下划线和英文句点。此值不能超过 255 个字符。

(可选)使用 <DisplayName> 元素在管理界面代理编辑器中给政策添加不同的自然语言名称标签。

不适用 必填
continueOnError

设置为 false 可在政策失败时返回错误。这是大多数政策的预期行为。

设置为 true,即使在政策失败后,仍可以继续执行流。 另请参阅:

false 可选
enabled

设置为 true 可强制执行政策。

设为 false关闭政策。即使政策仍附加到某个流,也不会强制执行该政策。

true 可选
async

此特性已弃用。

false 已弃用

<DisplayName> 元素

除了用于 name 特性之外,还可以用于在管理界面代理编辑器中给政策添加不同的自然语言名称标签。

<DisplayName>Policy Display Name</DisplayName>
默认

不适用

如果省略此元素,则会使用政策的 name 特性的值。

状态 可选
类型 字符串

<ClassName> 元素

指定在 Java 标注政策运行时执行的 Java 类的名称。该类必须包含在 <ResourceURL> 指定的 JAR 文件中。另请参阅如何创建 Java 标注

<JavaCallout name="MyJavaCalloutPolicy">
   <ResourceURL>java://MyJavaCallout.jar</ResourceURL>
   <ClassName>com.example.mypolicy.MyJavaCallout</ClassName>
</JavaCallout>
默认: 不适用
状态: 必填
类型: 字符串

<Properties> 元素

添加您可以在运行时从 Java 代码访问的新属性。

<Properties>
    <Property name="propName">propertyValue</Property>
</Properties>
默认:
状态: 可选
类型: 字符串

<Property> 元素

指定可在运行时从 Java 代码访问的属性。您必须为每个属性指定一个字面量字符串值;您无法在此元素中引用流变量。如需查看使用属性的有效示例,请参阅如何在 Java 标注中使用属性

<Properties>
    <Property name="propName">propertyValue</Property>
</Properties>
默认:
状态: 可选
类型: 字符串

特性

特性 说明 默认 状态
name

指定属性的名称。

不适用 必填。

<ResourceURL> 元素

此元素指定将在 Java 标注政策运行时执行的 Java JAR 文件。

您可以在 API 代理范围(API 代理软件包的 /apiproxy/resources/java 下方或 API 代理编辑器导航工具窗格的“脚本”部分中)或组织或环境范围中存储此文件,以便在多个 API 代理中重复使用,如资源文件中所述。

<JavaCallout name="MyJavaCalloutPolicy">
   <ResourceURL>java://MyJavaCallout.jar</ResourceURL>
   <ClassName>com.example.mypolicy.MyJavaCallout</ClassName>
</JavaCallout>
默认:
状态: 必填
类型: 字符串

错误参考信息

本部分介绍当此政策触发错误时返回的故障代码和错误消息,以及由 Apigee 设置的故障变量。在开发故障规则以处理故障时,请务必了解此信息。如需了解详情,请参阅您需要了解的有关政策错误的信息处理故障

运行时错误

政策执行时可能会发生这些错误。

故障代码 HTTP 状态 原因 修复
steps.javacallout.ExecutionError 500 当 Java 代码执行 JavaCallout policy 时抛出异常或返回 null 时发生。

部署错误

部署包含政策的代理时,可能会出现此类错误。

错误名称 故障字符串 HTTP 状态 发生的条件
ResourceDoesNotExist Resource with name [name] and type [type] does not exist 不适用 <ResourceURL> 元素中指定的文件不存在。
JavaCalloutInstantiationFailed Failed to instantiate the JavaCallout Class [classname] 不适用 <ClassName> 元素中指定的类文件不在 jar 中。
IncompatibleJavaVersion Failed to load java class [classname] definition due to - [reason] 不适用 请参阅故障字符串。支持的 Java 版本包括:Oracle JDK 7/8 和 OpenJDK 7/8
JavaClassNotFoundInJavaResource Failed to find the ClassName in java resource [jar_name] - [class_name] 不适用 请参阅故障字符串。
JavaClassDefinitionNotFound Failed to load java class [class_name] definition due to - [reason] 不适用 请参阅故障字符串。
NoAppropriateConstructor No appropriate constructor found in JavaCallout class [class_name] 不适用 请参阅故障字符串。
NoResourceForURL Could not locate a resource with URL [string] 不适用 请参阅故障字符串。

故障变量

此政策触发错误时设置这些变量。如需了解详情,请参阅您需要了解的有关政策错误的信息

变量 其中 示例
fault.name="fault_name" fault_name 是故障名称,如上面的运行时错误表中所列。故障名称是故障代码的最后一部分。 fault.name Matches "ExecutionError"
javacallout.policy_name.failed policy_name 是抛出故障的政策的用户指定名称。 javacallout.JC-GetUserData.failed = true

错误响应示例

{
   "fault":{
      "faultstring":"Failed to execute JavaCallout. [policy_name]",
      "detail":{
         "errorcode":"javacallout.ExecutionError"
      }
   }
}

故障规则示例

<FaultRule name="JavaCalloutFailed">
    <Step>
        <Name>AM-JavaCalloutError</Name>
    </Step>
    <Condition>(fault.name Matches "ExecutionError") </Condition>
</FaultRule>

架构

编译和部署

如需详细了解如何编译自定义 Java 代码并使用代理进行部署,请参阅如何创建 Java 标注

限制

下面是编写 Java 标注时需要考虑的限制:

  • 大多数系统调用都是不允许的。例如,您无法进行内部文件系统读取或写入。
  • 通过套接字访问网络。Apigee 会限制对 sitelocal、anylocal、loopback 和 linklocal 地址的访问。
  • 标注无法获取有关计算机上的当前进程、进程列表或 CPU/内存利用率的信息。尽管有些此类调用可能正常工作,但不受支持,并且可能随时会被主动停用。为了实现前向兼容性,您应该避免在代码中进行此类调用。
  • 不支持依赖于 Apigee 未随附的 Java 库。这些库仅适用于 Apigee 产品功能,并且不能保证各个版本之都可以使用该库。
  • 请勿在 Java 标注中使用 io.apigeecom.apigee 作为软件包名称。这些名称由其他 Apigee 模块保留和使用。

打包

将 JAR 放在 /resources/java 下的 API 代理中。如果您的 Java 标注依赖于打包为独立 JAR 文件的其他第三方库,则将这些 JAR 文件也放在 /resources/java 目录中,以确保在运行时正确加载它们。

如果您使用管理界面创建或修改代理,请添加新资源并指定其他依赖的 JAR 文件。如果有多个 JAR,只需将它们添加为其他资源。您无需修改政策配置来引用其他 JAR 文件。将其放入 /resources/java 即可。

如需了解如何上传 Java JAR,请参阅资源文件

如需展示如何使用 Maven 或 javac 打包和部署 Java 标注的详细示例,请参阅如何创建 Java 标注

Javadoc

GitHub 上此处提供了用于编写 Java 标注代码的 Javadoc。您需要克隆 HTML 或将其下载到您的系统,然后在浏览器中打开 index.html 文件。

使用说明和最佳做法

  • 使用多个 Java 标注时,请考虑将常见的 JAR 作为环境范围的资源上传。部署到同一环境时,相比将相同的 JAR 与多个代理软件包一起打包的做法相比,这种做法更高效。
  • 避免将同一 JAR 文件的多个副本或版本打包并部署到一个环境。例如,Apigee 建议您避免以下情形:
    • 将同一 JAR 作为代理软件包的一部分以及部署为环境资源。
    • 将 JAR 文件的一个版本部署为环境资源,将另一个版本部署为代理捆绑包的一部分。

    由于潜在的 ClassLoader 冲突,部署相同 JAR 的多个副本可能会在运行时导致不确定的行为。

  • Java 标注政策不包含实际代码。相反,Java 标注政策会引用 Java“资源”,并在执行 Java 代码的 API 流中定义步骤。您可以通过管理界面代理编辑器上传 Java JAR,也可以在本地开发的 API 代理中将其包含在 /resources/java 目录中。
  • 对于轻量级操作(例如对远程服务的 API 调用),我们建议使用 ServiceCallout 政策。请参阅服务标注政策
  • 对于与消息内容的相对简单互动(例如修改或提取 HTTP 标头、参数或消息内容),Apigee 建议使用 JavaScript 政策。