The main Bubble source repository. Contains the Bubble API server, the web UI, documentation and utilities. https://getbubblenow.com
Du kan inte välja fler än 25 ämnen Ämnen måste starta med en bokstav eller siffra, kan innehålla bindestreck ('-') och vara max 35 tecken långa.
 
 
 
 

79 rader
2.4 KiB

  1. #!/usr/bin/python3
  2. #
  3. # Replay a stream, as if mitmproxy were sending filter requests via the filter/apply API
  4. #
  5. # Usage:
  6. #
  7. # breplay_stream.py path_prefix
  8. #
  9. # path_prefix : some file prefix
  10. #
  11. # This will list all files matching the prefix, sort them, and play them back.
  12. # These files should come in triplets: a .url file, a .headers.json file, and a .data file/
  13. #
  14. # To capture requests for later playback:
  15. # * Set debug_stream_fqdn and debug_stream_uri in mitmproxy/bubble_config.py and restart mitmproxy servers
  16. # * Request a matching using a device whose traffic will be routed through the mitmproxy
  17. # * Capture files will be written to /tmp/bubble_stream_[request-id]_chunkXXXX.[url, headers.json, data]
  18. #
  19. import glob
  20. import json
  21. import requests
  22. import sys
  23. HEADER_FILTER_PASSTHRU = 'X-Bubble-Passthru'
  24. def log (message):
  25. print(message, file=sys.stderr, flush=True)
  26. def replay_stream (prefix, out):
  27. url_files = glob.glob(prefix+'*.url')
  28. if url_files is None or len(url_files) == 0:
  29. log('No files found matching prefix: '+prefix)
  30. return
  31. url_files.sort()
  32. for u in url_files:
  33. chunk_file = replace_suffix(u, '.data')
  34. headers_file = replace_suffix(u, '.headers.json')
  35. with open(u, mode='r') as f:
  36. url = f.read()
  37. with open(headers_file, mode='r') as f:
  38. headers = json.load(f)
  39. with open(chunk_file, mode='rb') as f:
  40. chunk = f.read()
  41. log('sending '+str(len(chunk))+' bytes to '+url)
  42. try:
  43. response_data = replay_request(url, headers, chunk)
  44. except Exception as e:
  45. log('error sending filter request: '+repr(e))
  46. raise e
  47. log('received '+str(len(response_data))+' bytes')
  48. if len(response_data) > 0:
  49. out.write(response_data)
  50. def replace_suffix(f, suffix):
  51. return f[0:f.rfind('.')] + suffix
  52. def replay_request(url, headers, chunk):
  53. response = requests.post(url, data=chunk, headers=headers)
  54. if not response.ok:
  55. log('replay_request: Error fetching ' + url + ', HTTP status ' + str(response.status_code))
  56. return b''
  57. elif HEADER_FILTER_PASSTHRU in response.headers:
  58. log('replay_request: server returned X-Bubble-Passthru, not filtering subsequent requests')
  59. return chunk
  60. return response.content
  61. if __name__ == "__main__":
  62. with open('/tmp/replay_response', mode='wb') as out:
  63. replay_stream(sys.argv[1], out)
  64. out.close()