Skip to content

Commit 534c7d5

Browse files
authored
Fix: Handle Werkzeug 3.x constraints in malware_tools_analyzer to resolve #3617 (#3618)
* Fix #3617: Handle Werkzeug 3.x multipart constraints and JSONDecodeError * fix: resolve ruff formatting and overlapping exception lint errors * fix: apply Werkzeug 3.x multipart constraints logic across all Flask containers
1 parent 9e43306 commit 534c7d5

7 files changed

Lines changed: 103 additions & 1 deletion

File tree

api_app/analyzers_manager/classes.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -290,7 +290,10 @@ def __raise_in_case_bad_request(name, resp, params_to_check=None) -> bool:
290290
if resp.status_code == 404:
291291
raise AnalyzerConfigurationException(f"{name} docker container is not running.")
292292
if resp.status_code == 400:
293-
err = resp.json().get("error", "")
293+
try:
294+
err = resp.json().get("error", "")
295+
except ValueError:
296+
err = resp.text or f"Bad Request in {name} docker container"
294297
raise AnalyzerRunException(err)
295298
if resp.status_code == 500:
296299
raise AnalyzerRunException(f"Internal Server Error in {name} docker container")

integrations/malware_tools_analyzers/app.py

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,9 +39,26 @@
3939
# Globals
4040
app = Flask(__name__)
4141
app.config["SECRET_KEY"] = secrets.token_hex(16)
42+
# Disable Werkzeug 3.x default form memory limit (500kB) to avoid false 400
43+
# errors on multipart requests.
44+
# See: https://werkzeug.palletsprojects.com/en/stable/changes/#version-3-1-0
45+
app.config["MAX_FORM_MEMORY_SIZE"] = None
46+
app.config["MAX_CONTENT_LENGTH"] = 1024 * 1024 * 1024 # 1GB
4247
executor = Executor(app)
4348
shell2http = Shell2HTTP(app, executor)
4449

50+
51+
# ensure error responses are JSON (not HTML) for flask-shell2http callers
52+
@app.errorhandler(400)
53+
def bad_request(e):
54+
return {"error": str(e)}, 400
55+
56+
57+
@app.errorhandler(413)
58+
def too_large(e):
59+
return {"error": str(e)}, 413
60+
61+
4562
# we are changeing the directory for execution of
4663
# artifacts script as it requires us to be in the
4764
# same directory

integrations/nuclei_analyzer/app.py

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,11 @@
3434
# Flask application instance with secret key
3535
app = Flask(__name__)
3636
app.config["SECRET_KEY"] = os.getenv("SECRET_KEY", os.urandom(24).hex())
37+
# Disable Werkzeug 3.x default form memory limit (500kB) to avoid false 400
38+
# errors on multipart requests.
39+
# See: https://werkzeug.palletsprojects.com/en/stable/changes/#version-3-1-0
40+
app.config["MAX_FORM_MEMORY_SIZE"] = None
41+
app.config["MAX_CONTENT_LENGTH"] = 1024 * 1024 * 1024 # 1GB
3742

3843
# Initialize the Executor for background task processing
3944
executor = Executor(app)
@@ -42,6 +47,17 @@
4247
shell2http = Shell2HTTP(app=app, executor=executor)
4348

4449

50+
# ensure error responses are JSON (not HTML) for flask-shell2http callers
51+
@app.errorhandler(400)
52+
def bad_request(e):
53+
return {"error": str(e)}, 400
54+
55+
56+
@app.errorhandler(413)
57+
def too_large(e):
58+
return {"error": str(e)}, 413
59+
60+
4561
@app.route("/health", methods=["GET"])
4662
def health_check():
4763
return {"status": "healthy"}, 200

integrations/pcap_analyzers/app.py

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,10 +39,26 @@
3939
# Globals
4040
app = Flask(__name__)
4141
app.config["SECRET_KEY"] = secrets.token_hex(16)
42+
# Disable Werkzeug 3.x default form memory limit (500kB) to avoid false 400
43+
# errors on multipart requests.
44+
# See: https://werkzeug.palletsprojects.com/en/stable/changes/#version-3-1-0
45+
app.config["MAX_FORM_MEMORY_SIZE"] = None
46+
app.config["MAX_CONTENT_LENGTH"] = 1024 * 1024 * 1024 # 1GB
4247
executor = Executor(app)
4348
shell2http = Shell2HTTP(app, executor)
4449

4550

51+
# ensure error responses are JSON (not HTML) for flask-shell2http callers
52+
@app.errorhandler(400)
53+
def bad_request(e):
54+
return {"error": str(e)}, 400
55+
56+
57+
@app.errorhandler(413)
58+
def too_large(e):
59+
return {"error": str(e)}, 413
60+
61+
4662
def intercept_suricata_result(context, future: Future) -> None:
4763
# 1. get current result object
4864
res = future.result()

integrations/phishing_analyzers/app.py

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,9 +29,26 @@
2929

3030
app = Flask(__name__)
3131
app.config["SECRET_KEY"] = secrets.token_hex(16)
32+
# Disable Werkzeug 3.x default form memory limit (500kB) to avoid false 400
33+
# errors on multipart requests.
34+
# See: https://werkzeug.palletsprojects.com/en/stable/changes/#version-3-1-0
35+
app.config["MAX_FORM_MEMORY_SIZE"] = None
36+
app.config["MAX_CONTENT_LENGTH"] = 1024 * 1024 * 1024 # 1GB
3237
executor = Executor(app)
3338
shell2http = Shell2HTTP(app, executor)
3439

40+
41+
# ensure error responses are JSON (not HTML) for flask-shell2http callers
42+
@app.errorhandler(400)
43+
def bad_request(e):
44+
return {"error": str(e)}, 400
45+
46+
47+
@app.errorhandler(413)
48+
def too_large(e):
49+
return {"error": str(e)}, 413
50+
51+
3552
shell2http.register_command(
3653
endpoint="phishing_extractor",
3754
command_name="/usr/local/bin/python3 /opt/deploy/phishing_analyzers/analyzers/extract_phishing_site.py",

integrations/thug/app.py

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,10 +38,26 @@
3838
# Globals
3939
app = Flask(__name__)
4040
app.config["SECRET_KEY"] = secrets.token_hex(16)
41+
# Disable Werkzeug 3.x default form memory limit (500kB) to avoid false 400
42+
# errors on multipart requests.
43+
# See: https://werkzeug.palletsprojects.com/en/stable/changes/#version-3-1-0
44+
app.config["MAX_FORM_MEMORY_SIZE"] = None
45+
app.config["MAX_CONTENT_LENGTH"] = 1024 * 1024 * 1024 # 1GB
4146
executor = Executor(app)
4247
shell2http = Shell2HTTP(app, executor)
4348

4449

50+
# ensure error responses are JSON (not HTML) for flask-shell2http callers
51+
@app.errorhandler(400)
52+
def bad_request(e):
53+
return {"error": str(e)}, 400
54+
55+
56+
@app.errorhandler(413)
57+
def too_large(e):
58+
return {"error": str(e)}, 413
59+
60+
4561
def intercept_thug_result(context, future: Future) -> None:
4662
"""
4763
Thug doesn't output result to standard output but to a file,

integrations/tor_analyzers/app.py

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,9 +37,26 @@
3737
"SECRET_KEY": __import__("secrets").token_hex(16),
3838
}
3939
app.config.update(CONFIG)
40+
# Disable Werkzeug 3.x default form memory limit (500kB) to avoid false 400
41+
# errors on multipart requests.
42+
# See: https://werkzeug.palletsprojects.com/en/stable/changes/#version-3-1-0
43+
app.config["MAX_FORM_MEMORY_SIZE"] = None
44+
app.config["MAX_CONTENT_LENGTH"] = 1024 * 1024 * 1024 # 1GB
4045

4146
executor = Executor(app)
4247
shell2http = Shell2HTTP(app, executor)
4348

49+
50+
# ensure error responses are JSON (not HTML) for flask-shell2http callers
51+
@app.errorhandler(400)
52+
def bad_request(e):
53+
return {"error": str(e)}, 400
54+
55+
56+
@app.errorhandler(413)
57+
def too_large(e):
58+
return {"error": str(e)}, 413
59+
60+
4461
# with this, we can make http calls to the endpoint: /onionscan
4562
shell2http.register_command(endpoint="onionscan", command_name="./bundled/onionscan")

0 commit comments

Comments
 (0)