cazyundee commited on
Commit
64e2bf0
·
1 Parent(s): d2bc83a

security: give the searx bridge its own gate key

Browse files

RESPIRE_SPACE_KEY guards the audio and inference routes; the searx
bridge now checks SEARX_API_KEY instead, so search access can be
rotated without touching the audio path. Both fail closed when unset.

🤖 Generated with Codebuff
Co-Authored-By: Codebuff <noreply@codebuff.com>

Files changed (1) hide show
  1. app.py +11 -3
app.py CHANGED
@@ -902,21 +902,29 @@ def _patched_create_app(blocks, **kwargs):
902
  import hmac as _hmac
903
 
904
  _SPACE_KEY = os.environ.get("RESpite_SPACE_KEY", "")
 
 
 
905
  _PROTECTED_PREFIXES = (
906
  "/respite/audio/",
907
  "/respite/search",
908
  "/respite/text/",
909
  "/respite/benchmark",
910
  # The searx bridge (searx_bridge.py) mounts under /respite/v2/ —
911
- # same compute, same key. Without this it is an open proxy: anyone
912
- # on the internet can run searches on the Space's IP for free.
913
  "/respite/v2/searx/",
914
  )
915
 
 
 
 
 
 
916
  @fa_app.middleware("http")
917
  async def _respite_key_gate(request, call_next):
918
  if request.url.path.startswith(_PROTECTED_PREFIXES):
919
- _SPACE_KEY = os.environ.get("RESPIRE_SPACE_KEY", "")
920
  if not _SPACE_KEY:
921
  return JSONResponse(
922
  {"error": "service not configured"}, status_code=503
 
902
  import hmac as _hmac
903
 
904
  _SPACE_KEY = os.environ.get("RESpite_SPACE_KEY", "")
905
+ # Which secret guards which prefix. The searx bridge gets its own key
906
+ # (SEARX_API_KEY) so rotating search access never touches the audio
907
+ # path; everything else shares RESPIRE_SPACE_KEY.
908
  _PROTECTED_PREFIXES = (
909
  "/respite/audio/",
910
  "/respite/search",
911
  "/respite/text/",
912
  "/respite/benchmark",
913
  # The searx bridge (searx_bridge.py) mounts under /respite/v2/ —
914
+ # without a gate it is an open proxy: anyone on the internet can
915
+ # run searches on the Space's IP for free.
916
  "/respite/v2/searx/",
917
  )
918
 
919
+ def _expected_key(path: str) -> str:
920
+ if path.startswith("/respite/v2/searx/"):
921
+ return os.environ.get("SEARX_API_KEY", "")
922
+ return os.environ.get("RESPIRE_SPACE_KEY", "")
923
+
924
  @fa_app.middleware("http")
925
  async def _respite_key_gate(request, call_next):
926
  if request.url.path.startswith(_PROTECTED_PREFIXES):
927
+ _SPACE_KEY = _expected_key(request.url.path)
928
  if not _SPACE_KEY:
929
  return JSONResponse(
930
  {"error": "service not configured"}, status_code=503