]> git.djapps.eu Git - pkg/ggml/sources/whisper.cpp/commitdiff
examples : update server.py to match github pages app [no ci] (#3004)
authorDaniel Bevenius <redacted>
Fri, 4 Apr 2025 08:23:53 +0000 (10:23 +0200)
committerGitHub <redacted>
Fri, 4 Apr 2025 08:23:53 +0000 (10:23 +0200)
This commit updates examples/server.py which is used to serve the wasm
examples locally. The changes include:

- Added a redirect from the root URL to /whisper.cpp.
  So now accessing http://localhost:8000/ will redirect to
  http://localhost:8000/whisper.cpp/ which matches the url for the app
  deployed to github pages.

- Custom handling for coi-serviceworker.js to serve it to avoid
  and error in the console. This file is not strictly necessary
  for the local server to work as the headers are provided already but
  it is nice to not have an error in the console.

- Fixed the shutdown of the server to ensure it exits cleanly
  on Ctrl+C. Previously it would continue to hang onto the port even
  after the processed had exited.

examples/server.py

index c2b189cfa8dd7c125d6ad5c6a67e350cfe4a6ea7..14f677220f368d2874d979dca78c2d05e81d4fe0 100644 (file)
 import http.server
 import socketserver
 import os
+import sys
 from pathlib import Path
+import urllib.parse
 
 SCRIPT_DIR = Path(__file__).parent.absolute()
 DIRECTORY = os.path.join(SCRIPT_DIR, "../build-em/bin")
 DIRECTORY = os.path.abspath(DIRECTORY)
 
+# The context root we want for all applications
+CONTEXT_ROOT = "/whisper.cpp"
+
 class CustomHTTPRequestHandler(http.server.SimpleHTTPRequestHandler):
     def __init__(self, *args, **kwargs):
         super().__init__(*args, directory=DIRECTORY, **kwargs)
 
     def do_GET(self):
-        # If requesting a worker file from any subdirectory
-        if '.worker.js' in self.path:
+        # Redirect root to the context root
+        if self.path == '/':
+            self.send_response(302)
+            self.send_header('Location', CONTEXT_ROOT + '/')
+            self.end_headers()
+            return
+
+        # Handle requests under the context root
+        if self.path.startswith(CONTEXT_ROOT):
+            # Remove the context root prefix to get the actual path
+            actual_path = self.path[len(CONTEXT_ROOT):]
+
+            if not actual_path:
+                self.send_response(302)
+                self.send_header('Location', CONTEXT_ROOT + '/')
+                self.end_headers()
+                return
+
+            if '.worker.js' in actual_path:
+                worker_file = os.path.basename(actual_path)
+                worker_path = os.path.join(DIRECTORY, worker_file)
+
+                if os.path.exists(worker_path):
+                    print(f"Found worker file: {worker_path}")
+                    self.path = '/' + worker_file
+                else:
+                    print(f"Worker file not found: {worker_path}")
+
+            elif actual_path == '/':
+                self.path = '/whisper.wasm/index.html'
+            elif actual_path.startswith('/bench.wasm/') or actual_path.startswith('/command.wasm/') or actual_path.startswith('/stream.wasm/'):
+                # Keep the path as is, just remove the context root
+                self.path = actual_path
+            # For all other paths under the context root
+            else:
+                # Check if this is a request to a file in whisper.wasm
+                potential_file = os.path.join(DIRECTORY, 'whisper.wasm', actual_path.lstrip('/'))
+                if os.path.exists(potential_file) and not os.path.isdir(potential_file):
+                    self.path = '/whisper.wasm' + actual_path
+                else:
+                    # Try to resolve the file from the base directory
+                    potential_file = os.path.join(DIRECTORY, actual_path.lstrip('/'))
+                    if os.path.exists(potential_file):
+                        self.path = actual_path
+
+        # For direct requests to worker files (without context root as these
+        # are in the build-em/bin directory
+        elif '.worker.js' in self.path:
             worker_file = os.path.basename(self.path)
             worker_path = os.path.join(DIRECTORY, worker_file)
 
             if os.path.exists(worker_path):
                 self.path = '/' + worker_file
 
+        # Handle coi-serviceworker.js separately
+        if 'coi-serviceworker.js' in self.path:
+            worker_file = "coi-serviceworker.js"
+            worker_path = os.path.join(SCRIPT_DIR, worker_file)
+            if os.path.exists(worker_path):
+                self.send_response(200)
+                self.send_header('Content-type', 'application/javascript')
+                self.end_headers()
+                with open(worker_path, 'rb') as file:
+                    self.wfile.write(file.read())
+                return
+            else:
+                print(f"Warning: Could not find {worker_path}")
+
         return super().do_GET()
 
     def end_headers(self):
         # Add required headers for SharedArrayBuffer
         self.send_header("Cross-Origin-Opener-Policy", "same-origin")
         self.send_header("Cross-Origin-Embedder-Policy", "require-corp")
-        self.send_header("Access-Control-Allow-Origin", "*");
+        self.send_header("Access-Control-Allow-Origin", "*")
         super().end_headers()
 
 PORT = 8000
 
-with socketserver.TCPServer(("", PORT), CustomHTTPRequestHandler) as httpd:
-    print(f"Serving directory '{DIRECTORY}' at http://localhost:{PORT}")
-    try:
-        httpd.serve_forever()
-    except KeyboardInterrupt:
-        print("\nServer stopped.")
+# Enable address reuse
+class CustomServer(socketserver.TCPServer):
+    allow_reuse_address = True
+
+try:
+    with CustomServer(("", PORT), CustomHTTPRequestHandler) as httpd:
+        print(f"Serving directory '{DIRECTORY}' at http://localhost:{PORT}")
+        print(f"Application context root: http://localhost:{PORT}{CONTEXT_ROOT}/")
+        try:
+            httpd.serve_forever()
+        except KeyboardInterrupt:
+            print("\nServer stopped.")
+            # Force complete exit
+            sys.exit(0)
+except OSError as e:
+    print(f"Error: {e}")
+    sys.exit(1)