Sri*_*ian 4 go amazon-web-services aws-lambda aws-lambda-go
查看Go文档 中官方AWS Lambda 函数处理程序中的使用全局状态部分https://docs.aws.amazon.com/lambda/latest/dg/golang-handler.html
建议初始化func init()
ie 中的所有全局状态。我们想要在多个 lambda 调用之间共享的任何包级别变量都放在此处。
我的理解是,每次 lambda 容器启动(即冷启动)时都会完成一次初始化。
我的问题是,是否可以使用func main()而不是做同样的事情func init()。由于运行的副作用,
使用func init()基本上使我的处理程序函数( )不可进行单元测试。将代码
移至似乎可以轻松解决此问题。使用vs
有什么副作用吗func LambdaHandlerfunc init()func init()func main()func main()func init()
代码示例
使用 func init()
package main
import (
"log"
"github.com/aws/aws-lambda-go/lambda"
"github.com/aws/aws-sdk-go/aws/session"
"github.com/aws/aws-sdk-go/service/s3"
"github.com/aws/aws-sdk-go/aws"
)
var invokeCount = 0
var myObjects []*s3.Object
func init() {
svc := s3.New(session.New())
input := &s3.ListObjectsV2Input{
Bucket: aws.String("examplebucket"),
}
result, _ := svc.ListObjectsV2(input)
myObjects = result.Contents
}
func LambdaHandler() (int, error) {
invokeCount = invokeCount + 1
log.Print(myObjects)
return invokeCount, nil
}
func main() {
lambda.Start(LambdaHandler)
}
Run Code Online (Sandbox Code Playgroud)
与
使用函数 main()
package main
import (
"log"
"github.com/aws/aws-lambda-go/lambda"
"github.com/aws/aws-sdk-go/aws/session"
"github.com/aws/aws-sdk-go/service/s3"
"github.com/aws/aws-sdk-go/aws"
)
var invokeCount = 0
var myObjects []*s3.Object
func LambdaHandler() (int, error) {
invokeCount = invokeCount + 1
log.Print(myObjects)
return invokeCount, nil
}
func main() {
svc := s3.New(session.New())
input := &s3.ListObjectsV2Input{
Bucket: aws.String("examplebucket"),
}
result, _ := svc.ListObjectsV2(input)
myObjects = result.Contents
lambda.Start(LambdaHandler)
}
Run Code Online (Sandbox Code Playgroud)
Jen*_*ens 10
我会提出以下建议(我们在很多 Go Lambda 中都成功使用了它)。
主程序
[...]
func (h *handler) handleRequest(ctx context.Context) error {
input := h.s3Client.ListObjectsV2Input{
Bucket: aws.String("examplebucket"),
}
[...]
}
type handler struct {
s3Client s3iface.S3API
}
// main is called only once, when the Lambda is initialised (started for the first time). Code in this function should
// primarily be used to create service clients, read environments variables, read configuration from disk etc.
func main() {
h := handler{
s3client: s3.New(session.New()),
}
lambda.Start(h.handleRequest)
}
Run Code Online (Sandbox Code Playgroud)
main_test.go
type ListObjectsV2Mock struct {
s3iface.S3API
output *s3.ListObjectsV2Output
}
func TestHandleRequest(t *testing.T) {
h := handler{
s3Client: &ListObjectsV2Mock{
output: &s3.ListObjectsV2Output{...},
},
}
err := h.HandleRequest(context.TODO())
if err != nil {
t.Fatalf("unexpected error: %v", err)
}
}
Run Code Online (Sandbox Code Playgroud)
显然,缺少很多代码(导入、错误处理等),但这就是要点。