在假定的字典中访问嵌套数据

时间:2021-02-07 20:41:25

标签: python aws-lambda slack-api

好吧,我被难住了。我搜索了所有我能想到的东西,从嵌套的 Dicts、Dicts 内的 Lists 内的 Dicts 到 JSON 引用,但不知道如何获取这些数据。

我有这个 AWS Lambda 处理程序,它正在读取 Slack 事件并简单地反转某人的消息,然后将其吐出回 Slack。但是,机器人可以对自己做出响应(创建一个无限循环)。我以为我已经解决了这个问题,但是,那是针对遗留问题的。我是 Python 笨蛋,那么如何引用这些数据?

数据(slack_body_dict 从下方打印):

{'token': 'NgapUeqidaGeTf4ONWkUQQiP', 'team_id': 'T7BD9RY57', 'api_app_id': 'A01LZHA7R9U', 'event': {'client_msg_id': '383aeac2-a436-4bad-8e19-7fa68facf916', 'type': 'message', 'text': 'rip', 'user': 'U7D1RQ9MM', 'ts': '1612727797.024200', 'team': 'T7BD9RY57', 'blocks': [{'type': 'rich_text', 'block_id': 'gA7K', 'elements': [{'type': 'rich_text_section', 'elements': [{'type': 'text', 'text': 'rip'}]}]}], 'channel': 'D01MK0JSNDP', 'event_ts': '1612727797.024200', 'channel_type': 'im'}, 'type': 'event_callback', 'event_id': 'Ev01MN8LJ117', 'event_time': 1612727797, 'authorizations': [{'enterprise_id': None, 'team_id': 'T7BD9RY57', 'user_id': 'U01MW6UK55W', 'is_bot': True, 'is_enterprise_install': False}], 'is_ext_shared_channel': False, 'event_context': '1-message-T7BD9RY57-D01MK0JSNDP'}

在我想检查的“授权”下有一个“is_bot”。我认为这会让机器人停止响应自己。但是,对于我的生活,我无法参考它。它似乎嵌套在那里。

我尝试了以下方法: def lambda_handler(api_event, api_context):

    print(f"Received event:\n{api_event}\nWith context:\n{api_context}")
    
    # Grab relevant information form the api_event
    slack_body_raw = api_event.get('body')
    slack_body_dict = json.loads(slack_body_raw)
    request_headers = api_event["headers"]
    
    print(f"!!!!!!!!!!!!!!!!!!!!!!!body_dict:\n{slack_body_dict}")
    print(f"#######################is_bot:\n{slack_body_dict('is_bot')}")
    print(f"#######################is_bot:\n{slack_body_dict("is_bot")}")
    print(f"#######################is_bot:\n{slack_body_dict(['is_bot']}")
    print(f"#######################is_bot:\n{slack_body_dict(["is_bot"]}")
    print(f"#######################is_bot:\n{slack_body_dict['authorizations']['is_bot']}")

如您所见,我完全不知道如何通过该变量来判断它是对还是错。每个“is_bot”打印引用都会导致错误。有人可以告诉我如何引用该变量或给我一些东西给谷歌吗?欣赏它。如果相关,代码如下。

import json
import os
from slack_sdk import WebClient
from slack_sdk.errors import SlackApiError

def is_challenge(slack_event_body: dict) -> bool:
    """Is the event a challenge from slack? If yes return the correct response to slack
    Args:
        slack_event_body (dict): The slack event JSON
    Returns:
        returns True if it is a slack challenge event returns False otherwise
    """
    if "challenge" in slack_event_body:
        LOGGER.info(f"Challenge Data: {slack_event_body['challenge']}")
        return True
    return False

def lambda_handler(api_event, api_context):
    
    # Grab relevant information form the api_event
    slack_body_raw = api_event.get('body')
    slack_body_dict = json.loads(slack_body_raw)
    request_headers = api_event["headers"]
    
    # This is to appease the slack challenge gods
    if is_challenge(slack_body_dict):
        challenge_response_body = {
            "challenge": slack_body_dict["challenge"]
        }
        return helpers.form_response(200, challenge_response_body)
        
    # This parses the slack body dict to get the event JSON
    slack_event_dict = slack_body_dict["event"]
    
    # Build the slack client.
    slack_client = WebClient(token=os.environ['BOT_TOKEN'])

    # We need to discriminate between events generated by 
    # the users, which we want to process and handle, 
    # and those generated by the bot.
    if slack_body_dict['is_bot']: #THIS IS GIVING ME THE ERROR. I WANT TO CHECK IF BOT HERE.
        logging.warning("Ignore bot event")
    else:
        # Get the text of the message the user sent to the bot,
        # and reverse it.
        text = slack_event_dict["text"]
        reversed_text = text[::-1]

        # Get the ID of the channel where the message was posted.
        channel_id = slack_event_dict["channel"]
        
        try:
            response = slack_client.chat_postMessage(
                channel=channel_id,
                text=reversed_text
            )
        except SlackApiError as e:
            # You will get a SlackApiError if "ok" is False
            assert e.response["error"]    # str like 'invalid_auth', 'channel_not_found'

1 个答案:

答案 0 :(得分:2)

数据结构为:

{
    "authorizations": [
        {
            "is_bot": true
        }
    ]
}

因此您需要首先索引 "authorizations",然后获取第一个项目 0,最后获取 "is_bot"

data["authorizations"][0]["is_bot"]

或者,您可以遍历所有授权并检查是否有任何(或全部)授权被标记为机器人,如下所示:

any(auth["is_bot"] for auth in slack_body_dict["authorizations"])