Skip to content
New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

new Serverless() not getting assigned correctly to this.serverless, Promise not resolving properly #126

Closed
ShnkeWeber opened this issue May 22, 2023 · 1 comment · Fixed by #127
Labels

Comments

@ShnkeWeber
Copy link

ShnkeWeber commented May 22, 2023

Expected behavior:

Code of function initializeServerless working properly and setting this.serverless to the generated sls

  async initializeServerless() {
    process.env.SLS_DEBUG = "*"

    const slsService = await ServerlessInvoker.loadServerlessYaml(
      path.join(this.servicePath, "serverless.yml")
    )
    const config = {
      serviceDir: path.dirname(this.servicePath),
      configurationFilename: "serverless.yml",
      configuration: slsService,
      commands: [],
      options: {},
    }
    const sls = new Serverless(config) // creates the new Serverless
    
    return sls.init().then(() => {
      sls.service.load().then(() => {
        sls.service.setFunctionNames({})
        sls.service.mergeArrays()
        sls.service.validate()
        **this.serverless = sls** // should set this.serverless to the created Serverless
      })
    })
  }

Actual behavior:

The initializeServerless function does not seem to set this.serverless = sls in time so that this.loadServerlessEvents throws an error as this.serverless is still null.
(TypeError: Cannot read properties of null (reading 'service') at ServerlessInvoker.loadServerlessEvents)

  async invoke(httpRequest, event, context) {
    // Read the serverless.yml file
    return this.initializeServerless()
      .then(() => **this.loadServerlessEvents()**) // error thrown by this function
      .then((httpEvents) => {
        // find the event that matches the specified httpRequest
        let httpEvent = httpEvents.find((e) => e.test(httpRequest))
        if (!httpEvent) {
          throw new Error(
            `Serverless http event not found for HTTP request "${httpRequest}" in service path "${this.servicePath}".`
          )
        }
async loadServerlessEvents() {
    let funcs = **this.serverless.service** // is null
      .getAllFunctions()
      .map((fname) => {
        let funcObj = this.serverless.service.getFunction(fname)
        let events = this.serverless.service.getAllEventsInFunction(fname)
        let f = {
          name: fname,
          handler: funcObj.handler,
          events: events.filter(
            (e) => Object.keys(e).includes("http") && e.http !== null
          ),
        }

Setting this.serverless = sls earlier or solved the problem for me:

    const sls = new Serverless(config)
   
    return sls.init().then(() => {
      **this.serverless = sls** // e.g. here
      sls.service.load().then(() => {
        sls.service.setFunctionNames({})
        sls.service.mergeArrays()
        sls.service.validate()
      })

Steps to reproduce the problem:

Create test class with a serverlessInvoker instance

private readonly serverlessInvoker = new ServerlessInvoker();

and exectue the invoke function

const response = await this.serverlessInvoker.invoke(
      'POST xyz',
      {}
    );

a serverless.yml

service: service

frameworkVersion: '3'

provider:
  name: aws
  runtime: nodejs18.x
  region: eu-central-1

resources:
  # externalize Resources to separated file to get support by IDE for cloudformation
  - ${file(serverless-resources.yml)}

serverless-resources.yml

Resources:
  OnlyApiRequestValidation:
    Type: "AWS::ApiGateway::RequestValidator"

Environment:

serverless-http-invoker 3.0.6
serverless 3.31.0
node 18
macOS 13.1.1

wahler added a commit to wahler/serverless-http-invoker that referenced this issue May 24, 2023
fix: ensure initializeServerless() runs sequentially

fixes activescott#126
activescott added a commit that referenced this issue May 25, 2023
…vice') at ServerlessInvoker.loadServerlessEvents" when calling invoke (#127)

ensures initializeServerless() runs sequentially as described in #126

fixes #126

Co-authored-by: scott willeke <scott@willeke.com>
@github-actions
Copy link

🎉 This issue has been resolved in version 3.0.7 🎉

The release is available on:

Your semantic-release bot 📦🚀

# for free to join this conversation on GitHub. Already have an account? # to comment
Labels
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant