Socketify.py - Maybe the fastest web framework for Python and PyPy
Tags: python, showdev, webdev, pubsub
Published: 2022-11-08 21:19:58

---
title: Socketify.py - Maybe the fastest web framework for Python and PyPy
published: true
description:  Really fast http and websockets for Python, PyPy3 and more

tags: python, showdev, webdev, pubsub,
# cover_image: https://direct_url_to_image.jpg
# Use a ratio of 100:42 for best results.
# published_at: 2022-11-08 19:52 +0000
---

This year i started a journey to bring a really fast framework for Http, Http2, Http3 and WebSockets to Python and PyPy. 

## The problems with japronto and uvloop
Japronto don't get any github updates since 2020 and don't get any src update since 2018, japronto don't support SSL, WebSockets, [`PyPy3`](https://www.pypy.org/), Windows or macOS Silicon.
I really needed good support + performance, not only performance.
Almost any solution out there have a really big performance hit when using PyPy3 or are not really fast enougth

## The Solution
We discover a really fast, small, and well maintained C++ Library called [uNetworking/uWebSockets](https://github.com/uNetworking/uWebSockets), but no C API available, so we create and adapt the full C API from [uNetworking/uWebSockets](https://github.com/uNetworking/uWebSockets) and will integrate libuv powered fetch and file IO, this same C API is used by [Bun](https://bun.sh/)

## :zap: Benchmarking
HTTP requests per second (Linux x64)

![image](https://raw.githubusercontent.com/cirospaciari/socketify.py/main/misc/bench-bar-graph.svg)

WebSocket messages per second (Linux x64)

![image](https://raw.githubusercontent.com/cirospaciari/socketify.py/main/misc/ws-bar-graph.svg)

It's a really an over simplificated microbenchmark, but shows a big difference between TechEmPower benchmarks using wrk and + 16 pipelining with an lua script, and of course will not hit 1 million req/s on my machine, running tfb tools in my machine socketify.py + PyPy3 hits 770k req/s vs 582k from japronto and in WebSockets almost 900k messages/s with PyPy3 and 860k with Python3 the same performance as [Bun](https://bun.sh),
with Falcon 35k messages/s and with Falcon with PyPy3 56k messages/s, node.js manages 192k, and still can get at least 30% or more performance once fully integrated with libuv + asyncio.


See more benchmark info here: https://github.com/cirospaciari/socketify.py#zap-benchmarks



## 💡 Features

- WebSocket with pub/sub support
- Fast and realiable Http/Https
- Support for Windows, Linux and macOS Silicon & x64
- Support for [`PyPy3`](https://www.pypy.org/) and [`CPython`](https://github.com/python/cpython)
- Dynamic URL Routing with Wildcard & Parameter support
- Sync and Async Function Support
- Really Simple API
- Fast and Encrypted TLS 1.3 quicker than most alternative servers can do even unencrypted, cleartext messaging
- Per-SNI HttpRouter Support
- Proxy Protocol v2
- Shared or Dedicated Compression Support
- Max Backpressure, Max Timeout, Max Payload and Idle Timeout Support
- Automatic Ping / Pong Support
- Per Socket Data

## :mag_right: Upcoming Features
- Fetch like API powered by libuv
- Async file IO powered by libuv
- Full asyncio integration with libuv
- Full Http3 support
- [`HPy`](https://hpyproject.org/) integration to better support [`CPython`](https://github.com/python/cpython), [`PyPy`](https://www.pypy.org/) and [`GraalPython`](https://github.com/oracle/graalpython)
- Hot Reloading


We created and adapt the full C API from [uNetworking/uWebSockets](https://github.com/uNetworking/uWebSockets) and will integrate libuv powered fetch and file IO, this same C API is used by [Bun](https://bun.sh/)


## 📦 Installation
For macOS x64 & Silicon, Linux x64, Windows

```bash
pip install git+https://github.com/cirospaciari/socketify.py.git
#or specify PyPy3
pypy3 -m pip install git+https://github.com/cirospaciari/socketify.py.git
#or in editable mode
pypy3 -m pip install -e git+https://github.com/cirospaciari/socketify.py.git@main#egg=socketify
```

## 🤔 Usage

Hello world app
```python
from socketify import App

app = App()
app.get("/", lambda res, req: res.end("Hello World socketify from Python!"))
app.listen(3000, lambda config: print("Listening on port http://localhost:%d now\n" % config.port))
app.run()
```

SSL version sample
``` python
from socketify import App, AppOptions

app = App(AppOptions(key_file_name="./misc/key.pem", cert_file_name="./misc/cert.pem", passphrase="1234"))
app.get("/", lambda res, req: res.end("Hello World socketify from Python!"))
app.listen(3000, lambda config: print("Listening on port http://localhost:%d now\n" % config.port))
app.run()
```

WebSockets
```python
from socketify import App, AppOptions, OpCode, CompressOptions

def ws_open(ws):
    print('A WebSocket got connected!')
    ws.send("Hello World!", OpCode.TEXT)

def ws_message(ws, message, opcode):
    #Ok is false if backpressure was built up, wait for drain
    ok = ws.send(message, opcode)
    
app = App()    
app.ws("/*", {
    'compression': CompressOptions.SHARED_COMPRESSOR,
    'max_payload_length': 16 * 1024 * 1024,
    'idle_timeout': 12,
    'open': ws_open,
    'message': ws_message,
    'drain': lambda ws: print('WebSocket backpressure: %i' % ws.get_buffered_amount()),
    'close': lambda ws, code, message: print('WebSocket closed')
})
app.any("/", lambda res,req: res.end("Nothing to see here!'"))
app.listen(3000, lambda config: print("Listening on port http://localhost:%d now\n" % (config.port)))
app.run()
```

And [click here](https://github.com/cirospaciari/socketify.py/tree/main/examples) more than 20 examples 

## :briefcase: Commercially supported
Socketify is an active project and will be maintained over time with security updates and new features and will be commercial support available

Check our github page: https://github.com/cirospaciari/socketify.py