'Is it possible to attach multiple schedule/cron events with one AWS Lambda function?

Currently my lambda function works successfully with one schedule event attached to it. Relevant excerpt from my template.yaml:

Resources:
  HelloWorldFunction:
    Type: AWS::Serverless::Function
    Properties:
      CodeUri: HelloWorldFunction
      Handler: helloworld.App::handleRequest
      Runtime: java11
      MemorySize: 512
      Environment:
        Variables:
          PARAM1: VALUE
      Events:
        CronHourlyEvent: # This already works
          Type: Schedule
          Properties:
            Description: Send John Doe
            Enabled: True
            Schedule: "cron(0 0/1 * * ? *)"
            Input: !Sub '{"name": "John Doe"}'

Lambda is triggered every one hour here and it works fine.

Now I would like to add another schedule event that triggers same lambda once a day at 12 Noon. One way of doing it would be to create a separate lambda and attach daily schedule event to that, but I don't want to create a new lambda just for that. I was hoping if I could attach two schedule events to the same lambda.

I could not find any example online where more that one schedule events were attached to a lambda, but I think following addition in template.yaml file would be needed:

Resources:
  HelloWorldFunction:
    Type: AWS::Serverless::Function
    Properties:
      CodeUri: HelloWorldFunction
      Handler: helloworld.App::handleRequest
      Runtime: java11
      MemorySize: 512
      Environment:
        Variables:
          PARAM1: VALUE
      Events:
        CronHourlyEvent: # this was already present
          Type: Schedule
          Properties:
            Description: Send John Doe
            Enabled: True
            Schedule: "cron(0 0/1 * * ? *)"
            Input: !Sub '{"name": "John Doe"}'
        CronDailyEvent: # added this
          Type: Schedule
          Properties:
            Description: Send Jane Doe
            Enabled: True
            Schedule: "cron(0 12 1/1 * ? *)"
            Input: !Sub '{"name": "Jane Doe"}'

I want to test it locally, so I downloaded and configured sam-sdk. But I don't think that supports running cron jobs locally. I was able to trigger events manually, but couldn't find any provision to run schedule jobs automatically based on cron expression provided.

So I would like to know:

  1. Whether we can attach 2 or more schedule/cron type events to an AWS lambda function?
  2. If yes, are the code changes I have done correct?

This will go directly into production, and I can't seem to figure out a way to test it locally.



Solution 1:[1]

I am using a config similar to the following, which perfectly works and satisfies my needs.

Resources:
    SayHelloWorldRule:
        Type: AWS::Events::Rule
        Properties:
            Description: The rule for greeting the world
            Name: ${self:provider.stage}-say-hello-world-rule
            ScheduleExpression: 'cron(0 7 * * ? *)'
            State: ENABLED
            Targets:
                -
                  Arn:
                    !Join [ ':', [ 'arn:aws:lambda', Ref: AWS::Region, Ref: AWS::AccountId, 'function', 'HelloWorldFunction' ] ]
                  Id: "GreetTheWorldDaily"
                  Input: '{"user": "Sudo user", "message": "Hello world!!!"}'

    SayGoodbyeWorldRule:
        Type: AWS::Events::Rule
        Properties:
            Description: "It's time to say goodbye"
            Name: ${self:provider.stage}-say-goodbye-rule
            ScheduleExpression: 'cron(30 22 * * ? *)'
            State: ENABLED
            Targets:
                -
                  Arn:
                      !Join [ ':', [ 'arn:aws:lambda', Ref: AWS::Region, Ref: AWS::AccountId, 'function', 'HelloWorldFunction' ] ]
                  Id: "SayGoodbyeDaily"
                  Input: '{"user": "Sudo user", "message": "Auf Wiedersehen!!!"}'

    PermissionForEventsToInvokeHelloWorldLambda:
        Type: AWS::Lambda::Permission
        Properties:
            FunctionName: HelloWorldFunction
            Action: "lambda:InvokeFunction"
            Principal: "events.amazonaws.com"

Solution 2:[2]

I might be a little late, but for anyone looking for a similar solution. Just use different names for the trigger.

  Events:
    Serverless:
      Type: Api
      Properties:
        Path: /serverless
        Method: get
    FirstConfigScheduledEvent:
      Type: Schedule
      Properties:
        Schedule: cron(30 21 * * ? *)
    SecondConfigScheduledEvent:
      Type: Schedule
      Properties:
        Schedule: cron(30 23 * * ? *)

Solution 3:[3]

The serverless docs do provide the following aspect to create multiple cron schedules -

# the example from our serverless.yml that runs every Monday at 03:15AM UTC
- schedule: cron(15 3 ? * MON *)
# run in 10-minute increments from the start of the hour on all working days
- schedule: cron(1/10 * ? * W *)
# run every day at 6:00PM UTC
- schedule: cron(0 18 * * ? *)

You can specify multiple schedule events for each function in case you’d like to combine the schedules. It’s possible to combine rate and cron events on the same function, too.

Source - Serverless

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 elbik
Solution 2 deep_c
Solution 3 Mohseen Mulla