MiniABS 1.1: HTTPS support
- Bundle current root certificates (Let's Encrypt, GTS, Sectigo, DigiCert G2, Amazon, ...) missing from Android 2.x's store (Roots.java, tools/gen_roots.py) - Ask once for unknown certificates, showing the SHA-256 fingerprint, and remember the answer; replaces "accept any certificate" (Trust*, Settings) - Local streaming proxy so Android 2.x's MediaPlayer can play https:// servers, with seeking and a fresh token per request (StreamProxy.java) - Tests over real TLS with good, expired, wrong-host, forged and self-signed certificates (test/make_pki.sh, TrustTest.java) - README: server setup for a legacy TLS 1.0 port Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
1 parent
4fe9eed870
commit
b7e43d7d61
24 files changed
+1326
-88
No files matched your search
+34
-1
@@ -14,6 +14,8 @@ from http.server import BaseHTTPRequestHandler, ThreadingHTTPServer
|
||||
|
||||
PORT = int(sys.argv[1])
|
||||
LEGACY = len(sys.argv) > 2 and sys.argv[2] == "legacy"
|
||||
CHAIN = sys.argv[3] if len(sys.argv) > 3 else None # serve HTTPS with this certificate chain
|
||||
AUDIO = bytes(i % 251 for i in range(200000))
|
||||
lock = threading.Lock()
|
||||
state = {"access": None, "refresh": None, "n": 0, "log": [], "progress": {}, "refreshes": 0}
|
||||
|
||||
@@ -159,6 +161,26 @@ class H(BaseHTTPRequestHandler):
|
||||
"currentTime": 600.0, "duration": 1807.5, "playMethod": 0,
|
||||
"audioTracks": [{"index": 1, "contentUrl": "/api/items/pod1/file/ino7",
|
||||
"mimeType": "audio/mpeg", "duration": 1807.5}]})
|
||||
if path == "/api/items/pod1/file/ino7":
|
||||
rng = self.headers.get("Range")
|
||||
if rng and rng.startswith("bytes="):
|
||||
a, _, b = rng[6:].partition("-")
|
||||
a = int(a)
|
||||
b = int(b) if b else len(AUDIO) - 1
|
||||
part = AUDIO[a:b + 1]
|
||||
self.send_response(206)
|
||||
self.send_header("Content-Range", "bytes %d-%d/%d" % (a, a + len(part) - 1, len(AUDIO)))
|
||||
else:
|
||||
part = AUDIO
|
||||
self.send_response(200)
|
||||
self.send_header("Content-Type", "audio/mpeg")
|
||||
self.send_header("Accept-Ranges", "bytes")
|
||||
self.send_header("Content-Length", str(len(part)))
|
||||
self.send_header("Connection", "close")
|
||||
self.end_headers()
|
||||
if method != "HEAD":
|
||||
self.wfile.write(part)
|
||||
return
|
||||
if path.startswith("/api/session/") and method == "POST":
|
||||
return self.send(200, "OK", "text/plain")
|
||||
if path.startswith("/api/me/progress/") and method == "PATCH":
|
||||
@@ -172,8 +194,19 @@ class H(BaseHTTPRequestHandler):
|
||||
def do_POST(self):
|
||||
self.handle_any("POST")
|
||||
|
||||
def do_HEAD(self):
|
||||
self.handle_any("HEAD")
|
||||
|
||||
def do_PATCH(self):
|
||||
self.handle_any("PATCH")
|
||||
|
||||
|
||||
ThreadingHTTPServer(("127.0.0.1", PORT), H).serve_forever()
|
||||
srv = ThreadingHTTPServer(("127.0.0.1", PORT), H)
|
||||
if CHAIN:
|
||||
import ssl
|
||||
ctx = ssl.SSLContext(ssl.PROTOCOL_TLS_SERVER)
|
||||
ctx.load_cert_chain(CHAIN, CHAIN + ".key")
|
||||
srv.socket = ctx.wrap_socket(srv.socket, server_side=True)
|
||||
# a TLS handshake the client rejects shows up as an error here; that's expected in tests
|
||||
srv.handle_error = lambda request, client_address: None
|
||||
srv.serve_forever()
|
||||
Reference in new issue
Block a user