anengelsen
anengelsen

Reputation: 93

AWS Lambda [ERROR] Function takes 1 positional argument but 2 were given

I am creating my (very first) Lambda function. The Lambda is designed to turn ON/OFF a Philips HUE bulb. The trigger for the Lambda function is an AWS IoT (Dash) Button.

However after triggering my Lambda function I am receiving the following error message:

[ERROR] TypeError: lambda_handler() takes 1 positional argument but 2 were given
Traceback (most recent call last):
  File "/var/runtime/bootstrap.py", line 131, in handle_event_request
    response = request_handler(event, lambda_context)

Can anyone offer any insight into what is wrong with my Python code? Thanks!

import requests,json

bridgeIP = "PublicIPAddress:999"
userID = "someone"
lightID = "2"

def lambda_handler(lightID):
 url = "http://"+bridgeIP+"/api/"+userID+"/lights/"+lightID
 r = requests.get(url)
 data = json.loads(r.text)
 if data["state"]["on"] == False:
     r = requests.put(url+"/state",json.dumps({'on':True}))
 elif data["state"]["on"] == True:
     r = requests.put(url+"/state",json.dumps({'on':False}))

lambda_handler(lightID)

Upvotes: 4

Views: 5639

Answers (2)

John Rotenstein
John Rotenstein

Reputation: 269101

Your handler function should be defined as:

def lambda_handler(event, context):
    lightID = event
    ...

From AWS Lambda Function Handler in Python - AWS Lambda:

event – AWS Lambda uses this parameter to pass in event data to the handler. This parameter is usually of the Python dict type. It can also be list, str, int, float, or NoneType type.

When you invoke your function, you determine the content and structure of the event. When an AWS service invokes your function, the event structure varies by service.

context – AWS Lambda uses this parameter to provide runtime information to your handler.

It is quite likely that your event merely contains the Light ID as shown by your code, but it is best to call it event to recognize that it is a value being passed into the Lambda function, but your code is then choosing to interpret it as the lightID.

Also, your code should not be calling the lambda_handler function. The AWS Lambda service will do this when the function is invoked.

Finally, you might want to take advantage of Python 3.x f-strings, which make prettier-format strings:

import requests
import json

bridgeIP = "PublicIPAddress:999"
userID = "someone"

def lambda_handler(event, context):
    lightID = event
    url = f"http://{bridgeIP}/api/{userID}/lights/{lightID}"

    r = requests.get(url)
    data = json.loads(r.text)

    r = requests.put(f"{url}/state", json.dumps({'on': not data["state"]["on"]}))

Upvotes: 4

ChidG
ChidG

Reputation: 3223

The error message is telling you that two positional arguments are given to your lambda_handler function, but the function is defined to accept only one.

Lambda automatically gives two arguments to a handler function, so you need to define your function to accept two arguments.

You can do that by changing your function definition to be:

def lambda_handler(lightID, lambda_context):

Upvotes: 1

Related Questions