apiKeyRequired 在 Google Cloud Endpoint 项目中不起作用



我有一个配置了Cloud Endpoint Framework的java 8项目。

我遵循了此处的文档:https://cloud.google.com/endpoints/docs/frameworks/java/get-started-frameworks-java

我尝试使用 API 密钥保护 API。我遵循了这里的文档:https://cloud.google.com/endpoints/docs/frameworks/java/restricting-api-access-with-api-keys-frameworks

问题是无论我是否设置 API 密钥,我都可以随时访问端点。

这是 API:

@Api(
name = "myApi",
title = "My API",
version = "v1",
description = "My API description",
apiKeyRequired = AnnotationBoolean.TRUE
)
public class MyApiEndpoint {
@ApiMethod(httpMethod = GET, path = "list", apiKeyRequired = AnnotationBoolean.TRUE)
public ApiEntityList list() throws Exception {
return new ApiEntityList();
}
}

这是网络.xml:

<?xml version="1.0" encoding="utf-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" version="3.1">
<filter>
<filter-name>endpoints-api-controller</filter-name>
<filter-class>com.google.api.control.extensions.appengine.GoogleAppEngineControlFilter</filter-class>
<init-param>
<param-name>endpoints.projectId</param-name>
<param-value>${app.deploy.project}</param-value>
</init-param>
<init-param>
<param-name>endpoints.serviceName</param-name>
<param-value>${app.deploy.project}.appspot.com</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>endpoints-api-controller</filter-name>
<servlet-name>EndpointsServlet</servlet-name>
</filter-mapping>
<filter>
<filter-name>endpoints-api-configuration</filter-name>
<filter-class>com.google.api.control.ServiceManagementConfigFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>endpoints-api-configuration</filter-name>
<servlet-name>EndpointsServlet</servlet-name>
</filter-mapping>
<servlet>
<servlet-name>EndpointsServlet</servlet-name>
<servlet-class>com.google.api.server.spi.EndpointsServlet</servlet-class>
<init-param>
<param-name>services</param-name>
<param-value>com.myproject.MyApiEndpoint</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>EndpointsServlet</servlet-name>
<url-pattern>/_ah/api/*</url-pattern>
</servlet-mapping>

appengine-web.xml:

<?xml version="1.0" encoding="utf-8"?>
<appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
<runtime>java8</runtime>
<threadsafe>true</threadsafe>
<service>core</service>
<url-stream-handler>urlfetch</url-stream-handler>
<system-properties>
<property name="java.util.logging.config.file" value="WEB-INF/logging.properties"/>
</system-properties>
<env-variables>
<env-var name="ENDPOINTS_SERVICE_NAME" value="${app.deploy.project}.appspot.com" />
</env-variables>
</appengine-web-app>

我在 Google Cloud Platform 项目中创建了 API 密钥作为新凭据,没有任何限制。

我可以在GCP上部署的openapi.json文件中看到以下行:

"/myApi/v1/list": {
"get": {
"operationId": "MyApiList",
"parameters": [ ],
"responses": {
"200": {
"description": "A successful response",
"schema": {
"$ref": "#/definitions/ApiEntityList"
}
}
},
"security": [
{
"api_key": [ ]
}
]
}
},
"securityDefinitions": {
"api_key": {
"type": "apiKey",
"name": "key",
"in": "query"
}
},

以下所有电话均未被拒绝,但我希望它们是:

  • https://core-dot-gcp-project.appspot.com/_ah/api/myApi/v1/list
  • https://core-dot-gcp-project.appspot.com/_ah/api/myApi/v1/list?key=FAKE_API_KEY
  • 来自未配置 API 密钥的 API 资源管理器的调用
  • 甚至从本地服务器:http://localhost:8080/_ah/api/myApi/v1/list

看起来apiKeyRequired注释参数没有任何影响。

我在这里错过了什么吗?

您是否确保您的API 已启用?我的意思是,当您创建云端点项目时,它还有效地将这些端点声明为"私有API"。然后,您必须启用它才能使 API 密钥生效

  • 在控制台中,键入"API 和服务"
  • 单击"+ 启用 API 和服务" ||侧边菜单中的"库">
  • 单击专用 API 侧边菜单中的"私有">
  • 您应该(希望(能够看到通过Cloud Endpoint创建的"API">

对于某些人来说,它似乎是自动完成的,但似乎有相当多的人没有。老实说,我不知道为什么会这样。

希望对您有所帮助!

我只是在测试它,并通过在 openapi.json 文件中添加除了 api 注释之外的顶级安全指令来使其工作。它应该看起来像这样:

{
"swagger": "2.0",
"info": {
"version": "1.0.0",
"title": "<PROJECT_ID>.appspot.com"
},
"host": "<PROJECT_ID>.appspot.com",
"basePath": "/_ah/api",
"schemes": [
"https"
],
"security": [
{
"api_key": [ ]
}
], 

之后,我运行 agiain 部署$ gcloud endpoints services deploy target/openapi-docs/openapi.json$ mvn appengine:deploy

我认为您没有使用默认的应用程序引擎服务,而是使用名为"core"的服务。

如果这是真的,那么我认为您需要更新以下内容以配置端点框架以了解要应用于哪个服务:

  1. 网站.xml:

筛选器定义中的参数名称endpoints.serviceName的参数值,用于com.google.api.control.extensions.appengine.GoogleAppEngineControlFilter${app.deploy.project}.appspot.com之前包含服务名称

<filter>
<filter-name>endpoints-api-controller</filter-name>
<filter-class>com.google.api.control.extensions.appengine.GoogleAppEngineControlFilter</filter-class>
<init-param>
<param-name>endpoints.projectId</param-name>
<param-value>${app.deploy.project}</param-value>
</init-param>
<init-param>
<param-name>endpoints.serviceName</param-name>
<param-value>core-dot-${app.deploy.project}.appspot.com</param-value>
</init-param>
</filter>
  1. appengine.web.xml:

ENDPOINTS_SERVICE_NAME在${app.deploy.project}.appspot.com之前包含服务名称的环境变量值

<env-variables>
<env-var name="ENDPOINTS_SERVICE_NAME" value="core-dot-${app.deploy.project}.appspot.com" />
</env-variables>

对于将来看到这个问题的任何人..我遇到了同样的问题,结果发现我已经更改了@ApiMethod中指定的路径,并且没有将新的 openAPI 文档部署到云端点。

我已经使用mvn appengine:deploy将我的项目部署到 App Engine 但我忘记了我还需要按照部署端点配置的本文档重新部署我的 openAPI 文档。所以它仍然使用我最初部署的旧资源/路径。当我将我的 openAPI 文档基本路径和我在@ApiMethod注释中的路径修复为我想要的路径时,我将其部署到云端点,然后 apiKeyRequired 注释再次工作!

最新更新