无法使用猫鼬从我的 lambda 连接到 Atlas 集群

Can't connect to Atlas cluster from my lambda using mongoose

我正在尝试使用 mongoose site

中的最后一个示例连接到集群

这是我使用 node14 和 typescript 的文件

import { APIGatewayProxyHandler } from "aws-lambda"

export { list as productsList } from "./products"

export const list: APIGatewayProxyHandler = (event, context, callback) => {
  callback(null, {
    statusCode: 200,
    body: `Hello from ${process.env.AWS_SAM_BRANCH}`,
  })
}
import mongoose from "mongoose"
import { APIGatewayProxyResult, Callback } from "aws-lambda"

let mongoConnection: Promise<typeof mongoose> | null = null

export const connectMongoose = async () => {
  if (mongoConnection == null) {
    const mongoURI = `mongodb+srv://USER:PASS@cluster0.ohjoj.mongodb.net/myFirstDB?retryWrites=true&w=majority`
    mongoConnection = mongoose
      .connect(mongoURI, { serverSelectionTimeoutMS: 3000 })
      .then((mongooseReply) => {
        console.log({ mongooseReply })
        return mongoose
      })
      .catch((mongooseError) => {
        console.log({ mongooseError })
        return mongoose
      })
    await mongoConnection
  }
  return mongoConnection
}

export const errorHandler = (error: unknown, callback: Callback<APIGatewayProxyResult>) => {
  console.error("catchedError", error)
  if (error instanceof Error) {
    callback(null, {
      statusCode: 400,
      headers: { "Content-Type": "application/json" },
      body: JSON.stringify({ error: error.message }),
    })
  } else {
    callback(null, {
      statusCode: 500,
      headers: { "Content-Type": "application/json" },
      body: JSON.stringify({ error: "Internal server error" }),
    })
  }
}
import { APIGatewayProxyHandler } from "aws-lambda"

import Model from "./model"
import { connectMongoose, errorHandler } from "../utils"

export const list: APIGatewayProxyHandler = (event, context, callback) => {
  try {
    connectMongoose()
    Model.find({}, (error: unknown, reply: unknown) => {
      if (error) throw error
      callback(null, {
        statusCode: 200,
        headers: { "Content-Type": "application/json" },
        body: JSON.stringify(reply),
      })
    })
  } catch (error) {
    errorHandler(error, callback)
  }
}
import mongoose from "mongoose"

const model = mongoose.model(
  "Product",
  new mongoose.Schema(
    {
      title: {
        type: String,
        required: true,
        maxLength: 256,
      },
      description: {
        type: String,
        required: true,
        maxLength: 2048,
      },
      count: {
        type: Number,
        required: true,
        min: 0,
        max: 1000 * 1000,
      },
    },
    {
      timestamps: true,
      versionKey: false,
    }
  )
)

export default model

这是存储库中的代码,其中包含用于使用 AWS SAM 进行部署的命令

我的应用中有 2 条路线

这有效并且 returns Hello from test 状态为 200

这不起作用,returns {"message":"Internal Server Error"} 状态为 500

这里是导出为 CSV 格式的 CloudWatch 日志

timestamp,message
1647203544609,"START RequestId: 83fd3fc8-1134-4ff4-a5f7-7e83a65159ce Version: $LATEST
"
1647203545742,"2022-03-13T20:32:25.685Z 83fd3fc8-1134-4ff4-a5f7-7e83a65159ce    INFO    {
  mongooseReply: <ref *1> Mongoose {
    connections: [ [NativeConnection] ],
    models: { Product: Model { Product } },
    events: EventEmitter {
      _events: [Object: null prototype] {},
      _eventsCount: 0,
      _maxListeners: undefined,
      [Symbol(kCapture)]: false
    },
    options: {
      pluralization: true,
      autoIndex: true,
      autoCreate: true,
      [Symbol(mongoose:default)]: true
    },
    _pluralize: [Function: pluralize],
    Schema: [Function: Schema] {
      reserved: [Object: null prototype],
      Types: [Object],
      ObjectId: [Function]
    },
    model: [Function (anonymous)],
    plugins: [ [Array], [Array], [Array], [Array], [Array], [Array] ],
    default: [Circular *1],
    mongoose: [Circular *1]
  }
}
"
1647203549616,"END RequestId: 83fd3fc8-1134-4ff4-a5f7-7e83a65159ce
"
1647203549616,"REPORT RequestId: 83fd3fc8-1134-4ff4-a5f7-7e83a65159ce   Duration: 5005.75 ms    Billed Duration: 5000 ms    Memory Size: 128 MB Max Memory Used: 76 MB  Init Duration: 366.30 ms    
"
1647203549616,"2022-03-13T20:32:29.616Z 83fd3fc8-1134-4ff4-a5f7-7e83a65159ce Task timed out after 5.01 seconds

"

this GitHub issue

中所述

几点建议:

  • 您应该在完全回调方法和完全承诺方法之间做出选择
  • 如果可以避免,请不要将 async / await 与 .then 语法混合使用
import mongoose from "mongoose"
import { APIGatewayProxyHandler } from "aws-lambda"

let mongoConnection: Promise<typeof mongoose> | null = null

const connectMongoose = async () => {
  if (mongoConnection == null) {
    const mongoURI = `mongodb+srv://YOUR_CLUSTER_URL`
    mongoConnection = mongoose
      .connect(mongoURI, { serverSelectionTimeoutMS: 3000 })
      .then((mongooseReply) => {
        console.log({ mongooseReply })
        return mongoose
      })
      .catch((mongooseError) => {
        console.log({ mongooseError })
        return mongoose
      })
    await mongoConnection
  }
  return mongoConnection
}

const Model = mongoose.model(
  "Product",
  new mongoose.Schema(
    {
      title: String,
      description: String,
    },
    {
      timestamps: true,
      versionKey: false,
    }
  )
)

export const myRoute: APIGatewayProxyHandler = async (event, context) => {
  try {
    await connectMongoose();
    const reply = await Model.find({}).exec();
    return {
      statusCode: 200,
      headers: { "Content-Type": "application/json" },
      body: JSON.stringify(reply),
    };
  } catch (error) {
    return {
     statusCode: 400,
     headers: { "Content-Type": "application/json" },
     body: "Server error",
    };
  }
}