patx/micropie
optimized session cookies, only set cookie session headers if needed
Commit 476ef4c · patx · 2025-01-29T02:48:13-05:00
Comments
No comments yet.
Diff
diff --git a/MicroPie.py b/MicroPie.py
index a46d47b..911ad7d 100644
--- a/MicroPie.py
+++ b/MicroPie.py
@@ -89,13 +89,12 @@ class Server:
cookies = self._parse_cookies(headers_dict.get("cookie", ""))
session_id = cookies.get("session_id")
+
if session_id and session_id in self.sessions:
self.session = self.sessions[session_id]
self.session["last_access"] = time.time()
else:
- session_id = str(uuid.uuid4())
- self.session = {"last_access": time.time()}
- self.sessions[session_id] = self.session
+ self.session = {}
self.body_params = {}
self.files = {}
@@ -169,16 +168,10 @@ class Server:
)
return
- session_cookie_header = (
- "Set-Cookie",
- f"session_id={session_id}; Path=/; HttpOnly; SameSite=Strict"
- )
- has_session_cookie = any(
- h[0].lower() == "set-cookie" and "session_id=" in h[1]
- for h in extra_headers
- )
- if not has_session_cookie:
- extra_headers.append(session_cookie_header)
+ if self.session:
+ session_id = cookies.get("session_id", str(uuid.uuid4()))
+ self.sessions[session_id] = self.session # Store session only if used
+ extra_headers.append(("Set-Cookie", f"session_id={session_id}; Path=/; HttpOnly; SameSite=Strict"))
await self._send_response(
send,
diff --git a/examples/hello_world/benchmarks/bench.sh b/examples/hello_world/benchmarks/bench.sh
new file mode 100755
index 0000000..d396110
--- /dev/null
+++ b/examples/hello_world/benchmarks/bench.sh
@@ -0,0 +1,56 @@
+#!/bin/bash
+
+# Test configuration
+TEST_DURATION="30s" # Test for 30 seconds
+NUM_THREADS="2" # Use 2 threads
+NUM_CONNECTIONS="1000" # 200 concurrent connections
+PORT="5000"
+URL="http://127.0.0.1:8000/"
+WRK_COMMAND="wrk -t$NUM_THREADS -c$NUM_CONNECTIONS -d$TEST_DURATION $URL"
+
+# Define the servers to benchmark
+declare -A servers
+servers["MicroPie"]="uvicorn micro:app --workers 4"
+servers["Starlette"]="uvicorn star:app --workers 4"
+servers["Quart"]="uvicorn qrt:app --workers 4"
+servers["FastAPI"]="uvicorn fast:app --workers 4"
+
+# Output file
+RESULTS_FILE="benchmark_results.txt"
+echo "=== Benchmark Results ===" > "$RESULTS_FILE"
+
+# Function to start server, run benchmark, and stop server
+benchmark_server() {
+ local name="$1"
+ local command="$2"
+
+ echo -e "\n=== Benchmarking $name ==="
+ echo -e "\n=== $name ===" >> "$RESULTS_FILE"
+
+ # Start the server in the background
+ eval "$command &"
+ SERVER_PID=$!
+
+ # Give the server some time to start
+ sleep 3
+
+ # Run wrk test
+ WRK_OUTPUT=$(eval "$WRK_COMMAND")
+
+ # Print and save results
+ echo "$WRK_OUTPUT"
+ echo "$WRK_OUTPUT" >> "$RESULTS_FILE"
+ echo -e "\n========================================\n" >> "$RESULTS_FILE"
+
+ # Stop the server
+ kill $SERVER_PID
+ wait $SERVER_PID 2>/dev/null
+}
+
+# Run benchmarks for each server
+for name in "${!servers[@]}"; do
+ benchmark_server "$name" "${servers[$name]}"
+done
+
+echo -e "\nBenchmarking complete. Results saved in $RESULTS_FILE"
+
diff --git a/examples/hello_world/benchmarks/benchmark_results.txt b/examples/hello_world/benchmarks/benchmark_results.txt
new file mode 100644
index 0000000..e61f94a
--- /dev/null
+++ b/examples/hello_world/benchmarks/benchmark_results.txt
@@ -0,0 +1,53 @@
+=== Benchmark Results ===
+
+=== Starlette ===
+Running 30s test @ http://127.0.0.1:8000/
+ 2 threads and 1000 connections
+ Thread Stats Avg Stdev Max +/- Stdev
+ Latency 463.73ms 93.44ms 793.29ms 72.98%
+ Req/Sec 1.07k 309.39 1.94k 66.00%
+ 64065 requests in 30.09s, 8.87MB read
+Requests/sec: 2129.04
+Transfer/sec: 301.86KB
+
+========================================
+
+
+=== FastAPI ===
+Running 30s test @ http://127.0.0.1:8000/
+ 2 threads and 1000 connections
+ Thread Stats Avg Stdev Max +/- Stdev
+ Latency 622.20ms 104.33ms 953.26ms 73.59%
+ Req/Sec 797.65 216.53 1.48k 69.40%
+ 47649 requests in 30.09s, 6.32MB read
+Requests/sec: 1583.67
+Transfer/sec: 215.17KB
+
+========================================
+
+
+=== Quart ===
+Running 30s test @ http://127.0.0.1:8000/
+ 2 threads and 1000 connections
+ Thread Stats Avg Stdev Max +/- Stdev
+ Latency 834.04ms 422.46ms 1.98s 61.02%
+ Req/Sec 597.05 288.80 1.51k 66.55%
+ 35581 requests in 30.10s, 4.92MB read
+Requests/sec: 1182.08
+Transfer/sec: 167.45KB
+
+========================================
+
+
+=== MicroPie ===
+Running 30s test @ http://127.0.0.1:8000/
+ 2 threads and 1000 connections
+ Thread Stats Avg Stdev Max +/- Stdev
+ Latency 559.16ms 119.78ms 1.03s 71.57%
+ Req/Sec 0.89k 344.42 1.95k 66.11%
+ 53082 requests in 30.09s, 8.26MB read
+Requests/sec: 1763.83
+Transfer/sec: 281.18KB
+
+========================================
+
diff --git a/examples/hello_world/benchmarks/fast.py b/examples/hello_world/benchmarks/fast.py
new file mode 100644
index 0000000..10cbb09
--- /dev/null
+++ b/examples/hello_world/benchmarks/fast.py
@@ -0,0 +1,7 @@
+from fastapi import FastAPI
+
+app = FastAPI()
+
[email protected]("/")
+async def index():
+ return "Hello World!"
diff --git a/examples/hello_world/benchmarks/micro.py b/examples/hello_world/benchmarks/micro.py
new file mode 100644
index 0000000..35aa090
--- /dev/null
+++ b/examples/hello_world/benchmarks/micro.py
@@ -0,0 +1,7 @@
+from MicroPie import Server
+
+class Root(Server):
+ async def index(self):
+ return f'Hello World!'
+
+app = Root()
diff --git a/examples/hello_world/benchmarks/qrt.py b/examples/hello_world/benchmarks/qrt.py
new file mode 100644
index 0000000..d0f99b1
--- /dev/null
+++ b/examples/hello_world/benchmarks/qrt.py
@@ -0,0 +1,7 @@
+from quart import Quart
+
+app = Quart(__name__)
+
[email protected]("/")
+async def index():
+ return "Hello World!"
diff --git a/examples/hello_world/benchmarks/star.py b/examples/hello_world/benchmarks/star.py
new file mode 100644
index 0000000..0634815
--- /dev/null
+++ b/examples/hello_world/benchmarks/star.py
@@ -0,0 +1,8 @@
+from starlette.applications import Starlette
+from starlette.responses import HTMLResponse
+from starlette.routing import Route
+
+async def index(request):
+ return HTMLResponse(f"Hello World!")
+
+app = Starlette(routes=[Route("/", index)])