Google App Engine 中可以进行长轮询吗?
-
26-09-2019 - |
题
我需要制作需要经常轮询服务器的应用程序,但GAE对请求有限制,因此发出大量请求可能会非常昂贵。是否可以使用长轮询并使请求等待最多 30 秒的更改?
解决方案
谷歌AppEngine上有一个新的功能频道API,与你有 一个可能性构建了良好的实时应用。
另一种解决方案是使用诸如了Mochiweb的第三部分彗星服务器 或扭曲用的iframe图案。
客户端1,等待事件:
client1 --Iframe Pattern--> Erlang/Mochiweb(HttpLongPolling):
客户机2,发送一个消息:
client2 --XhrIo--> AppEngine --UrlFetch--> Erlang/Mochiweb
要使用彗星图案了Mochiweb,理查德琼斯写了良好 主题(在谷歌:理查德琼斯一百万用户彗星的应用)。
其他提示
我们尝试在 App Engine 上实现类似 Comet 的长轮询解决方案,但结果好坏参半。
def wait_for_update(request, blob):
"""
Wait for blob update, if wait option specified in query string.
Otherwise, return 304 Not Modified.
"""
wait = request.GET.get('wait', '')
if not wait.isdigit():
return blob
start = time.time()
deadline = start + int(wait)
original_sha1 = blob.sha1
try:
while time.time() < deadline:
# Sleep one or two seconds.
elapsed = time.time() - start
time.sleep(1 if elapsed < 7 else 2)
# Try to read updated blob from memcache.
logging.info("Checking memcache for blob update after %.1fs",
elapsed)
blob = Blob.cache_get_by_key_name(request.key_name)
# Detect changes.
if blob is None or blob.sha1 != original_sha1:
break
except DeadlineExceededError:
logging.info("Caught DeadlineExceededError after %.1fs",
time.time() - start)
return blob
我看到的问题是长轮询请求之后的请求在长轮询请求后面被序列化(同步)。我可以在 Chrome 中查看跟踪并看到如下的时间线:
- 请求 1 已发送。GET(未修改)blob(等待更改)。
- 请求 2 已发送。修改斑点。
- 完全超时后,请求 1 返回(数据未修改)。
- 请求 2 在服务器上得到处理,并返回成功。
我使用了wireshark和Chrome/timeline来确认我正在通过与长轮询连接不同的TCP连接向服务器发送修改请求。因此,此同步必须发生在 App Engine 生产服务器上。据我所知,谷歌没有记录服务器行为的细节。
我认为等待通道 API 是我们从 App Engine 获得良好实时行为的最大希望。
我不认为长轮询是可能的。为谷歌应用服务引擎的默认请求超时是30秒。 在长轮询如果消息的时间超过30秒,以生成,那么它会失败。 你可能使用过短轮询更好。
另一种方法是“模拟”长轮询withing的30秒的限制。要做到这一点,如果消息不内到达,比如说20秒时,服务器可以发送一个“令牌”消息,而不是一个正常的消息时,要求客户消耗它和再次连接。
有似乎特征申请(及其在谷歌应用服务引擎接受)用于长轮询
不隶属于 StackOverflow