简体   繁体   中英

Increase timeout from slack slash command in python "operation_timeout"

I am running below python script which eventually runs shell script which gives me the list of running version in k8s namespace. Getting the result but it is taking time > 3sec. So, this is causing "operation_timeout" from slack. I am new to python, have gone with various docs regarding delay but that didn't help as those were very complex.

from subprocess import Popen, PIPE
from subprocess import check_output
from flask import Flask

def get_shell_script_output_using_communicate():
    session = subprocess.Popen(['./version.sh'], stdout=PIPE, stderr=PIPE)
    stdout, stderr = session.communicate()
    if stderr:
        raise Exception("Error "+str(stderr))
    return stdout.decode('utf-8')

def get_shell_script_output_using_check_output():
    stdout = check_output(['./version.sh']).decode('utf-8')
    return stdout

app = Flask(__name__)

@app.route('/test',methods=['POST'])
def home():
    return '`Version List` ```'+get_shell_script_output_using_check_output()+'```'

app.run(host='0.0.0.0', port=5002, debug=True)

Is there a way to get the response even if the command is taking more than 10sec? Thanks!

It is not possible to increase the default timeout from Slack to slash commands. It's always 3 seconds. But it's possible to send a delayed response for up to 30 minutes.

For that you need to first respond within 3 secs to acknowledge the initial request by sending back a HTTP 200 OK. Since that requires you to complete the current request, and terminate your main script, you need to run the function for the delayed response in parallel. That can be in a process, thread, by calling a celery task or any other means that allows you spawn a parallel running python function.

The parallel function can then respond to Slack by sending the message to the URL provided in response_url from the Slack request.

Here is an example implementation that uses threads:

import threading
from time import sleep
from flask import Flask, json, request
import requests

app = Flask(__name__) #create the Flask app

@app.route('/slash', methods=['POST'])
def slash_response():                
    """endpoint for receiving all slash command requests from Slack"""

    # get the full request from Slack
    slack_request = request.form

    # starting a new thread for doing the actual processing    
    x = threading.Thread(
            target=some_processing,
            args=(slack_request,)
        )
    x.start()

    ## respond to Slack with quick message
    # and end the main thread for this request
    return "Processing information.... please wait"


def some_processing(slack_request):
    """function for doing the actual work in a thread"""

    # lets simulate heavy processing by waiting 7 seconds
    sleep(7)

    # response to Slack after processing is finished
    response_url = slack_request["response_url"]    
    message = {        
        "text": "We found a result!"
    }
    res = requests.post(response_url, json=message)

if __name__ == '__main__':
    app.run(debug=True, port=8000) #run app in debug mode on port 8000

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM