【问题标题】:App engine warmup request not working for endpoints应用程序引擎预热请求不适用于端点
【发布时间】:2014-12-09 18:31:02
【问题描述】:

我有安卓客户端和谷歌应用引擎 java 服务器。尽管我看到了预热请求,但对我的端点的第一个请求(有时是 2-3 个请求)需要很长时间(8 - 20 秒甚至更多)。

这很烦人,因为另一个实例(我有 1 个常驻实例,我是唯一点击那里的用户,请求需要 100-200 毫秒,我每秒发送 1-3 个请求)可以在约 500 毫秒内处理此请求,但它会生成新实例,发出预热请求并将请求发送到新实例(即使我设置了 min_pending_latency = 10000)。示例:

I 2014-12-09 18:39:51.438 200 0 B 3657ms /_ah/warmup
I 2014-12-09 18:39:55.649 200 7.7 KB 8673ms /_ah/spi/com.sth.MyEndpoint.getMyEntity
I 2014-12-09 18:40:15.349 200 7.7 KB 9081ms /_ah/spi/com.sth.MyEndpoint.getMyEntity
I 2014-12-09 18:43:17.328 200 7.7 KB 135ms /_ah/spi/com.sth.MyEndpoint.getMyEntity    

我不希望我的用户在几十秒内随机出现延迟。我读了页面:
https://cloud.google.com/appengine/docs/java/config/appconfig#Java_appengine_web_xml_Warmup_requests
有一些关于“使用自定义预热 servlet”的内容,但我仍然不知道如何预热端点......如果答案确实存在,请指出来,告诉我 确切的 我该怎么办...

这里有人找到解决方案了吗?意思是,我希望我的新实例在启动端点后开始处理请求,因此它将在正常时间为来自真实用户的第一个传入请求提供服务,如通常的 100 - 200 毫秒(或至少在 1 秒以下)。我该怎么做?
请帮忙 ! :)

[编辑]

我的 web.xml(它有帮助):

<?xml version="1.0" encoding="utf-8" standalone="no"?><web-app xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="2.5" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">

<servlet>
<servlet-name>SystemServiceServlet</servlet-name>
<servlet-class>com.google.api.server.spi.SystemServiceServlet</servlet-class>
<load-on-startup>1</load-on-startup>
<init-param>
 <param-name>services</param-name>
 <param-value>com.sth.MyEndpoint</param-value>
</init-param>
</servlet>
<servlet-mapping>  
<servlet-name>SystemServiceServlet</servlet-name>
<url-pattern>/_ah/spi/*</url-pattern>
</servlet-mapping>
</web-app>

[编辑] 还有我的 appengine-web.xml:

<?xml version="1.0" encoding="utf-8"?>
<appengine-web-app xmlns="http://appengine.google.com/ns/1.0">
<application>myappname</application>
<version>version4</version>
<threadsafe>true</threadsafe>
<precompilation-enabled>true</precompilation-enabled>
<!-- Configure java.util.logging -->
<system-properties>
    <property name="java.util.logging.config.file" value="WEB-INF/logging.properties" />
</system-properties>
<automatic-scaling>
    <min-idle-instances>1</min-idle-instances>
    <max-idle-instances>1</max-idle-instances>
    <min-pending-latency>10.0s</min-pending-latency>
    <max-pending-latency>15.0s</max-pending-latency>
</automatic-scaling>
<warmup-requests-enabled>true</warmup-requests-enabled>
</appengine-web-app>

【问题讨论】:

  • 请帮忙?这太痛苦了。这是一个例子,我做了 3 次请求,2x I 2014-12-14 22:05:46.901 200 361 B 184ms /_ah/spi/com.sth.MyEndpoint.attack I 2014-12-14 22:05:58.530 200 409 B 182ms /_ah/spi/com.sth.MyEndpoint.attack I 2014-12-14 22:06:02.638 200 0 B 4129ms /_ah/warmup I 2014-12-14 22:06:22.058 200 367 B 11220ms /_ah/spi/com.sth.MyEndpoint.attack

标签: java android google-cloud-endpoints google-app-engine


【解决方案1】:

当这些请求发生时,我将详细记录您系统上发生的事件,我希望它能解决问题所在。请注意,请求日志上的时间戳会告诉您应用程序发送请求响应的时间,因此我将参考收到请求的时间在应用程序中减去它们的运行时间(日志行的ms 字段)

  • 您的第一个请求22:05:46.717 收到(我们称之为 T + 0 秒)

  • 您已将 min_idle_instances 设置为 1 并且还设置了 max_idle_instances 为 1,因此在任何给定时间系统只能有 1 个空闲实例 等待请求。当收到第一个请求时,它发送 它到那个很久以前旋转的实例,并且是空闲的 等待,只是等待为某人服务。 “实例 1”(我们将称之为)愉快地返回 回复184 ms

  • 您的第二个请求22:05:58.121 收到(大约T + 12 秒)

    (第二个请求也被路由到唯一的服务实例 - 实例 1。它在 182 ms 中返回响应)

  • 只要 App Master(系统中管理 根据您的配置和请求负载进行扩展和实例) 判断Instance 1不是空闲的,它发送一个预热请求 到新实例(“实例 2”)告诉它准备好。

  • 实例 2 的预热请求22:05:58.509 收到(T + 12 秒左右)

  • 根据需要完成多少工作来启动您的实例并使其准备好服务,在收到实例 2 的此预热请求之后将需要更短或更长的时间实际服务。您为系统服务 servlet 指定了 &lt;load-on-startup&gt;1&lt;/load-on-startup&gt; 的事实意味着它还将通过调用其 init 方法来加载 Endpoints SystemServiceServlet。这将进一步增加实例服务之前的时间。

    (请注意,预热请求需要 4.129 秒才能响应)

  • 第三个请求22:06:10.838 收到(T + 24 秒左右)

    (请注意,此请求是在实例 2 收到其预热请求后大约 12 秒,或在预热请求实际响应后大约 8 秒,即实例 2 上电时收到)。

    您定义了minimum_pending_latency = 10.0s 的事实通常意味着,当收到应用主程序确定没有可供服务的空闲实例的请求时,该请求将等待最少 10.0s(根据您的最大值,15.0s最大值),然后检查是否有可用的免费实例。事实上,您定义了minimum_idle_instances,但是,according to the docs,意味着minimum_pending_latency 应该“对应用程序性能的影响较小”...


这是您提供的日志向我们显示的所有信息。如果不查看更多代码,我无法确定到底发生了什么(例如,根据您包含的 jar 文件的数量,您的实例是否需要很短或很长时间才能启动),但这似乎是由于您使用的功能组合。也许第三个请求被放入待处理队列中,等待了 11 秒(高于 10 秒和低于 15 秒),最后得到了任一实例的服务(您是否在任一实例上看到了减速请求,假设您已定义a 1-idle-instance max?),将剩余的~200 ms 用于实际处理 API 调用,这与前两个请求的延迟一致。

我认为,如果您使用现有设置,鉴于您现在可以想象请求负载对扩展的影响,您可能会看到这种延迟消失了。

【讨论】:

  • 感谢您查看我的主题。从 22:05(T - 45 秒)到 22:07(T + 62 秒),这就是我的应用程序的所有流量 - 这 3 个请求和一次预热。我不明白为什么第三个请求等待了 10 到 15 秒,而我的一个实例始终处于打开状态,而且我没有流量,而且我的代码运行时间小于 200 毫秒,如您所见。我总共有 17 个罐子,5 个是 appengine-...,5 个是 datanucleus-...,gcm-server.jar,geronimo-jpa_2.0_spec-1.0.jar,jdo-api-3.0.1.jar,json -simple-1.1.jar、jsr107cache-1.1.jar、jta-1.1.jar、asm-4.0.jar
猜你喜欢
  • 1970-01-01
  • 2014-03-01
  • 1970-01-01
  • 2018-03-17
  • 1970-01-01
  • 2016-10-19
  • 2020-11-20
  • 1970-01-01
  • 2014-09-08
相关资源
最近更新 更多