Slack API로 요청을 확인합니다. 을 구현해 보자.

9657 단어 slack-apiPython3

하고 싶은 일



HTTP 요청이 Slack의 요청인지 확인
Slack의 요청 확인

AWS 주위



API Gateway를 사용했기 때문에 HTTP 헤더 편집

POST->메소드 요청->HTTP 요청 헤더


POST->통합 요청->HTTP 헤더



서버측 코드



flask로 쓰고 있습니다.
app = Flask(__name__)
@app.route("/", methods=["POST"])
def root():

    slack_signing_secret = b'MY_SLACK_SIGNING_SECRET'
    request_body = request.stream.read().decode()
    timestamp = request.headers['X-Slack-Request-Timestamp']
    if absolute_value(int(time.time()) - int(timestamp)) > 60 * 5:
        #タイムスタンプが5分以上ずれていたら、それはDDoS攻撃の可能性が高いので無視する。
        return
    sig_basestring = 'v0:' + timestamp + ':' + request_body
    my_signature = 'v0=' + hmac.new(
            slack_signing_secret,
            sig_basestring.encode("utf-8"),
            hashlib.sha256
            ).hexdigest()
    slack_signature = request.headers['X-Slack-Signature']
    if hmac.compare_digest(my_signature, slack_signature):
        print("request is ok")
    else:
        print("bad request")

도서관에



python-slackclient 에 함수가 있습니다. 고맙습니다.
from slack import WebClient
client = WebClient(slack_bot_token)

app = Flask(__name__)
@app.route("/", methods=["POST"])
def root():

    slack_signing_secret = "MY_SLACK_SIGNING_SECRET"
    request_body = request.stream.read().decode()
    timestamp = request.headers['X-Slack-Request-Timestamp']
    signature = request.headers["X-Slack-Signature"]
    if absolute_value(int(time.time()) - int(timestamp)) > 60 * 5:
        #タイムスタンプが5分以上ずれていたら、それはDDoS攻撃の可能性が高いので無視する。
        return

    valification_flag = client.validate_slack_signature(
            signing_secret=slack_signing_secret,
            data=request_body,
            timestamp=timestamp,
            signature=signature
            )

    if valification_flag:
        print("request is ok")
    else:
        print("bad request")

어려움



원래 flask.request.form 로 페이로드를 취득했습니다만,flask.request.stream 를 사용하면 byte 가 되어 버립니다.

그리고 어느 쪽인가를 사용하면 request 의 내용은 비워집니다.
그래서 이번에는 byte to json를 다음과 같이 썼습니다.
import urllib.parse
dict_data = json.loads(urllib.parse.unquote_plus(request_body).split("=",1)[1])

무리

추가 (2020.3.31)



앞의 항목에서 parseunquote 에는 다음의 2 종류가 있다.
urllib.parse.unquote()
urllib.parse.unquote_plus()

이번에는 unquote_plus()를 사용해야 했기 때문에 수정했다.

좋은 웹페이지 즐겨찾기