【发布时间】:2016-10-27 06:24:51
【问题描述】:
众所周知,AWS lambda 可能重用早期创建的处理程序对象,并且确实做到了(参见FAQ):
问:AWS Lambda 会复用函数实例吗?
为了提高性能,AWS Lambda 可能会选择保留 您的函数并重用它来服务后续请求,而不是 创建一个新副本。您的代码不应假定这将始终 发生。
问题与Java 并发有关。如果我有一个处理程序的类,请说:
public class MyHandler {
private Foo foo;
public void handler(Map<String,String> request, Context context) {
...
}
}
那么,在这里访问和使用对象变量foo 是否是线程安全的?
换句话说:AWS lambda 是否可以同时为不同的调用使用同一个对象?
EDIT 我的函数在基于事件的源上进行处理,特别是由 API Gateway 方法调用。
EDIT-2 当您想实现某种与外部资源的连接池时,就会出现此类问题,因此我想将与外部资源的连接保持为对象变量。它实际上可以按预期工作,但我担心并发问题。
EDIT-3 更具体地说,我想知道:AWS lambda 处理程序的实例是否可以共享公共堆(内存)?我必须指定这个额外的细节,以防止答案列出关于 java 线程安全对象的明显和众所周知的事情。
【问题讨论】:
-
IMO“保留函数的实例并重用它”与“使用相同的对象”完全相同。而且很可能同时发生。
-
@zapl 当然,但同样,无状态风格并不意味着它们不能是线程安全的。
-
@Shibashis 我在每秒数百个请求的情况下使用它。如果我的上下文是单线程的,我自然不会问这样的问题。
-
你的问题不清楚。如果在您的函数中,请确保您的函数以线程安全的方式访问 foo 变量。由于 lambda 函数的重用,您不应该担心线程安全。它仅在函数不处理另一个请求时才重用。有点像对象池。该函数的每个实例都在底层容器中运行并且是独立的。
-
@Shibashis 我的问题实际上不清楚什么?我问了一个精确的问题:关于重用处理程序实例的可能性,它是否是线程安全的使用对象变量?什么不清楚?关于评论的第二部分 - 如果您有指向描述此功能的确切文档的链接,您可以提供它作为答案,它将被接受。
标签: java multithreading amazon-web-services concurrency aws-lambda