High-performance Python bindings for nng (nanomsg-next-gen)
Project description
nng
High-performance Python bindings for nng (nanomsg-next-gen), written in Cython.
Nanomsg-next-gen (NNG) is a messaging library written in C. It provides a small, consistent API for building distributed applications around a set of well-defined communication patterns: request-reply, publish-subscribe, pipeline, pair, survey, and bus. The library handles message framing, back-pressure, reconnection, and transport selection, so application code can focus on the protocol logic.
Table of contents
- Why use a library like NNG rather than sockets directly?
- Why yet another Python wrapper for NNG?
- What I like about NNG
- Installation
- Quick start
- Async support
- Transports
- Communication patterns
- TLS support
- Performance
- On the use of AI
- License
Why use a library like NNG rather than sockets directly?
The Python standard library has a lot of available functions for communicating with sockets between processes on the same or different computers.
Sockets are essentially data queues managed by the kernel and used to communicate between processes. When connecting to a website via TCP, or when receiving a video stream via UDP, you use sockets.
With the Python standard library, there are essentially two main ways to use sockets:
- via the
socketlibrary. - via
asyncio.
NNG provides an abstraction on top, enabling shorter and easier-to-read code. It provides a socket-like interface, except that:
- The socket can listen on or bind to several interfaces at the same time.
- It is possible to send or wait on a message before a peer has connected
- Rather than handling individual connections with connected peers, you use a socket type that has implicit handling of peers. For instance a PUB socket will send a copy of any message sent to all connected peers.
- Message semantics is directly handled (low level sockets are typically configured to receive a bytestream rather than messages). A background thread handles receiving incoming messages and queuing them (you need to quickly handle the reception of incoming messages to prevent blocking reception if the kernel queue is full).
- Reconnection is handled automatically
Underneath, NNG is similar to a dedicated thread running asyncio. Both use epoll/kqueue/iocp to quickly detect sockets ready for reading/writing. It is programmed in C and fully thread-safe.
Because it uses a dedicated thread, you can get asynchronous I/O without asyncio. submit_recv returns a future that resolves when a message is received. However this Python library also integrates NNG to an existing asyncio loop.
Don't use NNG if:
- You want the lowest latency possible. In terms of latency, asyncio NNG (
arecv) > raw asyncio > NNG (recv) > raw socket. If you want below, don't use Python. See PERFORMANCE.md for detailed benchmarks and interpretation. - You want to share heavy amount of data. NNG is based on TCP and similar, while for video streaming or remote desktop, UDP with custom handling of lost packets is more appropriate. For inter-process large data sharing, shared memory is preferred over named pipes/unix sockets (which NNG ipc uses), as they avoid kernel copies. If you don't need to maximize performance and can accept some data copies, NNG is appropriate though.
- You need to integrate with another protocol (HTTP, custom, etc)
Use NNG if:
- You are building distributed or multi-process applications and want well-defined message semantics without managing low-level socket details.
- You need multiple communication patterns (request-reply, pub-sub, pipeline, pair, survey, bus) with a consistent, interchangeable API.
- You want automatic reconnection, back-pressure, and message framing out of the box.
- You want to mix blocking calls,
asynciocoroutines, andconcurrent.futureswithin the same codebase. - You need concurrent request handling on a server without the overhead of one thread per client (use contexts).
- You want the same API for ipc, tcp or inproc endpoints
- You don't want to manage each connection individually
- You don't want to require asyncio to get asynchronous server/client connections, send/recv.
Why yet another Python wrapper for NNG?
Two Python wrappers for NNG already existed when this project was started.
My motivation for writing a third one came from practical experience with ZeroMQ. When looking for a first message library to experiment upon, it is quite natural to start with ZeroMQ, which is heavily used. However, what seemed simple on paper, lead to a lot of boilerplate to have things work properly. I was not satisfied and gave up on the topic for some time. After coming back on the topic, I decided to give NNG a try. However, the existing wrappers did not feel as complete as PyZMQ: docstrings were sparse, error handling was inconsistent, and there were no benchmarks to help make informed choices.
A more specific concern was asyncio overhead. The ZeroMQ Python bindings had measurable overhead in async code, which I had partially mitigated with a custom selector backed by zmq_poll. NNG's callback-based completion model seemed more amenable to tight asyncio integration. Achieving that level of integration requires Cython, which the other wrappers did not use.
The result is a library with:
- Full type annotations and docstrings on all public symbols.
- A
.pyistub file automatically generated from the compiled extension. - Synchronous send/recv, async (
await), and thread-safeconcurrent.futuresvariants on every socket and context. - Explicit error hierarchy: every nng error code maps to a typed Python exception.
- Benchmarks of the various send/recv alternatives, with and without encryption.
- Examples covering every communication pattern.
What I like about NNG
Having used both ZeroMQ and NNG, I found that ZeroMQ quickly pushes you toward ROUTER sockets everywhere, which removes constraints but adds significant complexity that is easy to get wrong (client failure handling, heartbeats, etc). NNG, by contrast, provides richer built-in socket behaviour and more flexibility. Need to handle several clients concurrently? Just open several contexts on the same socket. The context system is powerful and lightweight, and was well-designed to keep application logic simple.
Another key difference is that NNG is designed to be fully thread-safe. Closing a socket from another thread is safe and will simply cause pending operations to fail with NngClosed, making it much easier to write clean shutdown code without worrying about synchronization or cancellation. NNG also has built-in TLS support.
Installation
The package requires Python 3.11 or later and a C++ compiler. NNG is bundled as a submodule and compiled automatically.
pip install nng
For TLS support (tls+tcp://, wss://), install the pre-built package that bundles Mbed TLS:
pip install nng-ssl
The nng-ssl wheel is drop-in compatible with nng; the same import nng works for both. Install one or the other, not both.
To build from source:
git clone --recurse-submodules https://github.com/axeldavy/python-nng.git
cd python-nng
pip install .
See TLS support for instructions on enabling TLS at build time.
Quick start
REP / REQ
The REQ/REP pattern implements synchronous request-reply. The requester sends a message and blocks until a reply arrives. The replier receives one request at a time and must send exactly one reply before receiving the next.
import nng
# Server side (in a thread or separate process)
rep = nng.RepSocket()
rep.add_listener("tcp://127.0.0.1:5555").start()
while True:
msg = rep.recv()
rep.send(b"pong")
# Client side
req = nng.ReqSocket()
req.add_dialer("tcp://127.0.0.1:5555").start()
req.send(b"ping")
reply = req.recv()
print(reply) # "pong"
To handle multiple clients concurrently on the server side without threads, open independent contexts. Each context maintains its own request-reply state machine:
import asyncio
import nng
async def handle(ctx: nng.Context) -> None:
while True:
msg = await ctx.arecv()
await ctx.asend(b"pong")
async def main() -> None:
rep = nng.RepSocket()
rep.add_listener("tcp://127.0.0.1:5555").start()
workers = [rep.open_context() for _ in range(8)]
await asyncio.gather(*(handle(ctx) for ctx in workers))
PUB / SUB
The PUB/SUB pattern distributes messages from one publisher to any number of subscribers. Subscribers receive only messages whose body starts with a registered prefix.
import nng
# Publisher
pub = nng.PubSocket()
pub.add_listener("tcp://127.0.0.1:5556").start()
pub.send(b"news.sports result of the match")
pub.send(b"news.weather it will rain")
# Subscriber
sub = nng.SubSocket()
sub.add_dialer("tcp://127.0.0.1:5556").start()
sub.subscribe(b"news.sports") # receive only sports messages
# sub.subscribe(b"") # or subscribe to everything
msg = sub.recv()
There is no acknowledgment: if a subscriber cannot consume messages fast enough, the oldest messages in its buffer are dropped by default. The publisher is never blocked by a slow subscriber.
PUSH / PULL
The PUSH/PULL pattern distributes work items across a pool of workers. Each message goes to exactly one worker, chosen by load-balancing.
import nng
# Work distributor
push = nng.PushSocket()
push.add_listener("tcp://127.0.0.1:5557").start()
for i in range(100):
push.send(f"task-{i}")
# Worker (run several of these in parallel)
pull = nng.PullSocket()
pull.add_dialer("tcp://127.0.0.1:5557").start()
while True:
task = pull.recv()
print("processing", task)
PAIR
The PAIR pattern connects exactly two sockets in a bidirectional channel. It is the simplest pattern: each side can send and receive freely. Once a peer has connected, no other peer can connect (even after a disconnect). This makes it ideal for in-process communication between threads, or for one-to-one protocols between processes.
import nng
srv = nng.PairSocket()
srv.add_listener("inproc://myapp").start()
cli = nng.PairSocket()
cli.add_dialer("inproc://myapp").start()
cli.send(b"hello")
print(srv.recv()) # "hello"
Async support
Every socket and context exposes three ways to send and receive:
| Method | Description |
|---|---|
send / recv |
Blocking call. Releases the GIL while waiting. |
asend / arecv |
Coroutines. Use with await inside an asyncio event loop. |
submit_send / submit_recv |
Returns a concurrent.futures.Future, which resolves upon completion. |
Note that it is possible to mix them, or call them concurrently from multiple threads. In addition it is worth noting that Ctrl-C is fully supported (unlike in some other libraries), even with send and recv.
import asyncio
import nng
async def main() -> None:
rep = nng.RepSocket()
rep.add_listener("tcp://127.0.0.1:5558").start()
req = nng.ReqSocket()
req.add_dialer("tcp://127.0.0.1:5558").start()
await req.asend(b"hello")
msg = await rep.arecv()
await rep.asend(msg.to_bytes().upper())
reply = await req.arecv()
print(reply) # "HELLO"
asyncio.run(main())
The library also provides async generators arecv_ready and asend_ready for advanced use; each yields once every time the socket transitions from not-ready to ready.
Transports
All transports are selected by URL scheme and are otherwise interchangeable from application code.
| Scheme | Description |
|---|---|
tcp://host:port |
TCP/IP. Accepts both IPv4 and IPv6. Use tcp4:// or tcp6:// to force one version. |
ipc:///path |
Unix domain sockets (POSIX) or named pipes (Windows). |
inproc://name |
In-process communication within the same Python process. Zero-copy where possible. |
abstract://name |
Linux abstract namespace sockets. Not persisted to the filesystem. |
tls+tcp://host:port |
TCP with TLS. Requires a TLS-enabled build (see below). |
ws://host:port/path |
WebSocket. |
wss://host:port/path |
WebSocket over TLS. |
Listeners bind to an address; dialers connect to one. The distinction is orthogonal to the protocol role: a REP socket can dial and a REQ socket can listen.
To bind to an ephemeral TCP port, pass port 0 in the listener URL. The assigned port can be retrieved from listener.port after start() returns.
Communication patterns
| Socket pair | Pattern | Use case |
|---|---|---|
ReqSocket / RepSocket |
Request-reply | RPC, command-response |
PubSocket / SubSocket |
Publish-subscribe | Event fan-out, topic feeds |
PushSocket / PullSocket |
Pipeline | Task queues, stream processing |
PairSocket / PairSocket |
Pair | Bidirectional point-to-point channel |
SurveyorSocket / RespondentSocket |
Survey | Voting, service discovery |
BusSocket / BusSocket |
Bus | All-to-all broadcast mesh |
Each pattern has well-defined send/recv semantics. Violating them — for instance calling send twice on a ReqSocket without an intervening recv — raises NngState.
TLS support
By default, nng is built without TLS support to keep the package pure MIT.
Pre-built wheel with TLS
The easiest way to get TLS support is the nng-ssl package on PyPI. It bundles
Mbed TLS 4.1.0 (Apache-2.0 license) compiled as a static library and requires no
extra system dependencies:
pip install nng-ssl
nng-ssl installs as the nng Python package, so existing code is unchanged.
Do not install both nng and nng-ssl in the same environment.
Build from source with Mbed TLS (auto-fetched)
To build nng-ssl locally, Mbed TLS is downloaded and compiled automatically
during the cmake configure step (internet access required at build time):
git clone --recurse-submodules https://github.com/axeldavy/python-nng.git
cd python-nng
cp builtin_tls/pyproject.toml pyproject.toml
pip install .
Build from source with a system TLS library
You can also build nng (not nng-ssl) against an independently installed TLS
library:
# Mbed TLS (system-installed)
pip install . --config-settings "cmake.define.NNG_ENABLE_TLS=ON" --config-settings "cmake.define.NNG_TLS_ENGINE=mbed"
# OpenSSL
pip install . --config-settings "cmake.define.NNG_ENABLE_TLS=ON" --config-settings "cmake.define.NNG_TLS_ENGINE=openssl"
# wolfSSL
pip install . --config-settings "cmake.define.NNG_ENABLE_TLS=ON" --config-settings "cmake.define.NNG_TLS_ENGINE=wolf"
Once built, TLS connections use the tls+tcp:// scheme. Configuration is handled through TlsConfig:
import nng
srv_cfg = nng.TlsConfig.for_server(
cert_pem=open("server.crt").read(),
key_pem=open("server.key").read(),
ca_pem=open("ca.crt").read(), # required for mutual TLS
auth_mode=nng.TLS_AUTH_REQUIRED,
min_version=nng.TLS_VERSION_1_3,
)
rep = nng.RepSocket()
lst = rep.add_listener("tls+tcp://0.0.0.0:0", tls=srv_cfg)
lst.start()
print(f"listening on port {lst.port}")
Three authentication modes are available:
| Constant | Meaning |
|---|---|
TLS_AUTH_NONE |
No peer certificate is requested. |
TLS_AUTH_OPTIONAL |
A peer certificate is verified if presented. |
TLS_AUTH_REQUIRED |
A peer certificate is required (mutual TLS). This is the default for clients. |
TLS 1.2 and 1.3 are supported. The minimum and maximum protocol versions can be set via min_version and max_version using the TLS_VERSION_1_2 and TLS_VERSION_1_3 constants.
A comparison of plain, libsodium-encrypted, and TLS-encrypted throughput at various payload sizes is available in examples/PAIR/secure_subscriber/bench_overhead.py.
Performance
See PERFORMANCE.md for detailed benchmarks and interpretation.
In brief: on a local machine the async round-trip overhead (excluding cipher cost) is on the order of a few microseconds for inproc, and grows with transport cost for IPC and TCP. TLS throughput depends heavily on whether the TLS backend was compiled with hardware AES acceleration.
On the use of AI
Much of the writing has been assisted by AI (Claude Sonnet 4.6), in particular the benchmark code and the unit tests. I have 12 years of Python experience, and more in C/C++. I have written another Cython-based library DearCyGui. Thus while AI has been a great help, I have extensively reviewed, extended, and modified the code and documentation, and I am confident that the code is of good quality. If you find any issue, please open an issue or a PR.
License
python-nng is licensed under the MIT License. See LICENSE for more details.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distributions
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file nng-0.2.0.tar.gz.
File metadata
- Download URL: nng-0.2.0.tar.gz
- Upload date:
- Size: 968.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0cd735ced3374ca15cf32cb5456dd40bd45266eb3de26e5c091488ef10509f73
|
|
| MD5 |
eb06d08548c417a4a4c013288ffdc1a6
|
|
| BLAKE2b-256 |
0f8d374b9cc9f2013139e46c171fb05fe63a55e04387389117d2ca17697cd921
|
File details
Details for the file nng-0.2.0-cp314-cp314t-win_amd64.whl.
File metadata
- Download URL: nng-0.2.0-cp314-cp314t-win_amd64.whl
- Upload date:
- Size: 1.1 MB
- Tags: CPython 3.14t, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
43602a15bdbec85b05bbfb1a222bf2c8a9adc2b874c577883b76d5db1ebfa941
|
|
| MD5 |
fd5e1b8699e7bba011ba00b0f4daf34c
|
|
| BLAKE2b-256 |
46bac0ee48a8355f0063bca3efa742f80e5df255dd47f9570a9ef97233daeff9
|
File details
Details for the file nng-0.2.0-cp314-cp314t-manylinux_2_28_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp314-cp314t-manylinux_2_28_x86_64.whl
- Upload date:
- Size: 913.3 kB
- Tags: CPython 3.14t, manylinux: glibc 2.28+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
ec7da3cb927f2c24cfcd4818bf6907ace3cd72a8080f36a60a0c66da9d338858
|
|
| MD5 |
ae1a844057c94beaadc9ec357fef7d05
|
|
| BLAKE2b-256 |
47feea79efcff83aa9e77b373b867c0c2e02e6e488eee7d57bae1036d0ff4468
|
File details
Details for the file nng-0.2.0-cp314-cp314t-macosx_11_0_arm64.whl.
File metadata
- Download URL: nng-0.2.0-cp314-cp314t-macosx_11_0_arm64.whl
- Upload date:
- Size: 788.0 kB
- Tags: CPython 3.14t, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
6657f43bf43a94fb83226b139313fdcaae990c6fed939729bb1b4f1b3b8a832a
|
|
| MD5 |
f94557e7fd0b7e6afffc87f7a91719ab
|
|
| BLAKE2b-256 |
cab9d6cd1473ad7f9c6521d0d3078a9144e4d160ed39b60e41e58f95ba5c621d
|
File details
Details for the file nng-0.2.0-cp314-cp314t-macosx_10_15_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp314-cp314t-macosx_10_15_x86_64.whl
- Upload date:
- Size: 828.4 kB
- Tags: CPython 3.14t, macOS 10.15+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
1647baca76e1c1ded46a74dd2c7f02c0750be573a2e0b939fd4fab4a126c51bf
|
|
| MD5 |
9bb23f64867ad053c28ca04543e4203b
|
|
| BLAKE2b-256 |
409624cf71ac9ee2d202c095917acc0325e63f58fad03883d64209aa189ca608
|
File details
Details for the file nng-0.2.0-cp314-cp314-win_amd64.whl.
File metadata
- Download URL: nng-0.2.0-cp314-cp314-win_amd64.whl
- Upload date:
- Size: 1.0 MB
- Tags: CPython 3.14, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
41cc879968c4ee940adfa813706b1d3abff4175b90f3e00cce542da29dfb2eca
|
|
| MD5 |
f1a5012db828f1544f640aff5d98846e
|
|
| BLAKE2b-256 |
443f756c9c927c1f096adb7c9586a58ae8ea49ccc3ffe5ae579731979e09827d
|
File details
Details for the file nng-0.2.0-cp314-cp314-manylinux_2_28_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp314-cp314-manylinux_2_28_x86_64.whl
- Upload date:
- Size: 917.9 kB
- Tags: CPython 3.14, manylinux: glibc 2.28+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0057108125776b308da4cf4d36cdcfe1d77d4829633612f400d9f3169e93864f
|
|
| MD5 |
10fb9cfc87855477ca4b559e00451027
|
|
| BLAKE2b-256 |
22cb46845b68318bfb777fb9c17a72982ab4822fff8322a7aeab1ed98909e7ce
|
File details
Details for the file nng-0.2.0-cp314-cp314-macosx_11_0_arm64.whl.
File metadata
- Download URL: nng-0.2.0-cp314-cp314-macosx_11_0_arm64.whl
- Upload date:
- Size: 770.3 kB
- Tags: CPython 3.14, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
c2b4c74c1985a07ff4a34a4a964184b17afce7e488aa70b27b244e948762e75e
|
|
| MD5 |
de2539ecb278bd943aa03efc0b1aa7e4
|
|
| BLAKE2b-256 |
f7c908a974e60eecce575250de300d777c242cd58ec9bdc3ebc57b44da2f8485
|
File details
Details for the file nng-0.2.0-cp314-cp314-macosx_10_15_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp314-cp314-macosx_10_15_x86_64.whl
- Upload date:
- Size: 814.1 kB
- Tags: CPython 3.14, macOS 10.15+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
57909773e8607636ccf39f09c5f7a121e411dd62e88be552828711a5b3c811dd
|
|
| MD5 |
d8e2fc4ed4e4904ed25e7e0f0e92e026
|
|
| BLAKE2b-256 |
8ce62f84481f8efa5e51893055e5acc16bc4160d5e8b5285888bb05ab2ad810f
|
File details
Details for the file nng-0.2.0-cp313-cp313t-win_amd64.whl.
File metadata
- Download URL: nng-0.2.0-cp313-cp313t-win_amd64.whl
- Upload date:
- Size: 1.1 MB
- Tags: CPython 3.13t, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
2146609bbd756366ccec493850d85e8a980cbc04eb03c0bea4e8b9157eafc1a6
|
|
| MD5 |
a3c780cd69275d29f1267d4c242473fb
|
|
| BLAKE2b-256 |
3208e55c13052c17fae250bf51a3ef727d8ec434d76c6528ebbf1d3266548e97
|
File details
Details for the file nng-0.2.0-cp313-cp313t-manylinux_2_28_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp313-cp313t-manylinux_2_28_x86_64.whl
- Upload date:
- Size: 912.2 kB
- Tags: CPython 3.13t, manylinux: glibc 2.28+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
ad8c84d10c4ae08ea89082367e3179bf966bb4c1e6eff52a57a3b9944522f093
|
|
| MD5 |
f5e0c1cd7d92c1a2337bbd8dec4fb90e
|
|
| BLAKE2b-256 |
5a925f9cea5f6b670ced7e95b51c555b8f68874fe884fb841dea9498350d5843
|
File details
Details for the file nng-0.2.0-cp313-cp313t-macosx_11_0_arm64.whl.
File metadata
- Download URL: nng-0.2.0-cp313-cp313t-macosx_11_0_arm64.whl
- Upload date:
- Size: 786.9 kB
- Tags: CPython 3.13t, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
36d3619f731f48b1499ed2eca775e7e8759edbb90dd9a3f5f648833c9610579b
|
|
| MD5 |
459eb44484d1b29e2681d32786ad03e2
|
|
| BLAKE2b-256 |
466b4474705f5bc2a33192eca07cb96c9b0bb3dfe3eb3c7e37e8239e5b0c96f0
|
File details
Details for the file nng-0.2.0-cp313-cp313t-macosx_10_15_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp313-cp313t-macosx_10_15_x86_64.whl
- Upload date:
- Size: 826.7 kB
- Tags: CPython 3.13t, macOS 10.15+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
d6ffd1f9603da1893fe34d27c7a402e27aa24a5d95e3f731de6532b4abfa1b08
|
|
| MD5 |
acc1b3d7f2bebdd72eb96d66a05068ee
|
|
| BLAKE2b-256 |
80bf8690cbe0a71d6130e5bf7c68966fe2dc071a6b08b532b69639afaaf7e861
|
File details
Details for the file nng-0.2.0-cp313-cp313-win_amd64.whl.
File metadata
- Download URL: nng-0.2.0-cp313-cp313-win_amd64.whl
- Upload date:
- Size: 1.0 MB
- Tags: CPython 3.13, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
f7ff275ba9a91607969440a3260275e6427975a80d2a727c9716b2b23468af22
|
|
| MD5 |
4b85d611460ff3f104c392751ff5db7f
|
|
| BLAKE2b-256 |
d337ff1c01f2cab8f4975f124ab7045b9a53e8e21e6220a076ac1e16474d2e65
|
File details
Details for the file nng-0.2.0-cp313-cp313-manylinux_2_28_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp313-cp313-manylinux_2_28_x86_64.whl
- Upload date:
- Size: 915.7 kB
- Tags: CPython 3.13, manylinux: glibc 2.28+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
3306f1fb3938c53b6044e83e93ee61c6c8a11f36813346a1a6d7b10b9b715608
|
|
| MD5 |
ee6d312917d857b208da5207f31ac75b
|
|
| BLAKE2b-256 |
22cc49543082a701d8244c573023de82fb6316f54c48ff9ab36f2e33b1bdd28d
|
File details
Details for the file nng-0.2.0-cp313-cp313-macosx_11_0_arm64.whl.
File metadata
- Download URL: nng-0.2.0-cp313-cp313-macosx_11_0_arm64.whl
- Upload date:
- Size: 767.7 kB
- Tags: CPython 3.13, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
92062be73f3b5f235f06b307b51f718ddc3879f55e9d672596f4c93390c74943
|
|
| MD5 |
3cb95d56c857d7511769b34ac229564b
|
|
| BLAKE2b-256 |
cc3ec8586bdea0c9c5e2604d9cdd0ae6e37886066758902642db5113745668fd
|
File details
Details for the file nng-0.2.0-cp313-cp313-macosx_10_15_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp313-cp313-macosx_10_15_x86_64.whl
- Upload date:
- Size: 812.5 kB
- Tags: CPython 3.13, macOS 10.15+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
5ab0a960af9a709688d59edf805c75b0f618985fa1b767f32e3d3099f70a76e7
|
|
| MD5 |
393dadcb7e454a66880e2a233c022fa0
|
|
| BLAKE2b-256 |
92067c0de04682fd65ad5b3e6367b7dc1251d014416276823c97ff052d2e5cf1
|
File details
Details for the file nng-0.2.0-cp312-cp312-win_amd64.whl.
File metadata
- Download URL: nng-0.2.0-cp312-cp312-win_amd64.whl
- Upload date:
- Size: 1.0 MB
- Tags: CPython 3.12, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
8b69fd0080ca74512bdef67f7412eb5ef913fd31d067105411432d338184010b
|
|
| MD5 |
db3636845ad5edcd8cd2c7d8e63432a9
|
|
| BLAKE2b-256 |
aef9eb360c48d0b471cd29e4c965604ee868e78155e08ec6e3b58f599f86b5ba
|
File details
Details for the file nng-0.2.0-cp312-cp312-manylinux_2_28_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp312-cp312-manylinux_2_28_x86_64.whl
- Upload date:
- Size: 915.3 kB
- Tags: CPython 3.12, manylinux: glibc 2.28+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
1a1985d3ba1938e573ead1d99e91f034ba39d0417cc664d4d130cf00c17cc884
|
|
| MD5 |
431022fbe701661e028260f8a3e5216c
|
|
| BLAKE2b-256 |
9af5515cb46cce41283669f30bb4d77f4b6efe77e876cf60420c489d03ace9e7
|
File details
Details for the file nng-0.2.0-cp312-cp312-macosx_11_0_arm64.whl.
File metadata
- Download URL: nng-0.2.0-cp312-cp312-macosx_11_0_arm64.whl
- Upload date:
- Size: 768.6 kB
- Tags: CPython 3.12, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b2cef47ffb3f28e19bc455d191239cf4bcb8bd4fb67e1a93ed89f8e18af701d3
|
|
| MD5 |
9cdefedeff404581be84d71dd2238fc0
|
|
| BLAKE2b-256 |
7432d4ab58381f10d515caf9d028b3fa3e768bd23774b87fb2a94d6c6f46a139
|
File details
Details for the file nng-0.2.0-cp312-cp312-macosx_10_15_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp312-cp312-macosx_10_15_x86_64.whl
- Upload date:
- Size: 813.2 kB
- Tags: CPython 3.12, macOS 10.15+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b1f6a8ba78a7d88cbbdc361c22afe717bc3dbf2b9d96ad446378c1cdb1a14576
|
|
| MD5 |
530b3ff1db7ccd750826711e81ed7554
|
|
| BLAKE2b-256 |
56b17b7d71f711f4b0b3dcad77d3afd5f5cdb80b3a5333b07cbb6c8dfc47b3d5
|
File details
Details for the file nng-0.2.0-cp311-cp311-win_amd64.whl.
File metadata
- Download URL: nng-0.2.0-cp311-cp311-win_amd64.whl
- Upload date:
- Size: 1.0 MB
- Tags: CPython 3.11, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
a457cde8cc9e237ef71fc312604062f4f90cff20109e9ef81fb72fe8025f5564
|
|
| MD5 |
e20c4c159570b583cae6bae2c9a4b7fe
|
|
| BLAKE2b-256 |
0bdccc68125b0db757a933184b2701779d03316db680ee4203977fe0eb2a1507
|
File details
Details for the file nng-0.2.0-cp311-cp311-manylinux_2_28_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp311-cp311-manylinux_2_28_x86_64.whl
- Upload date:
- Size: 930.2 kB
- Tags: CPython 3.11, manylinux: glibc 2.28+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
2cc2338b5d4dbdb6e060bf5fc38373324d9d6b4278936554cffdf1e01ed4c7e1
|
|
| MD5 |
2a6dd7175a98bfce695b8c5343167da0
|
|
| BLAKE2b-256 |
3456b7fa6b8e14666823fe3520ed94ed17843b99737363c403198348588a7c64
|
File details
Details for the file nng-0.2.0-cp311-cp311-macosx_11_0_arm64.whl.
File metadata
- Download URL: nng-0.2.0-cp311-cp311-macosx_11_0_arm64.whl
- Upload date:
- Size: 767.1 kB
- Tags: CPython 3.11, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
f6332257158d83a0b10ffef4be463668c5cf6da5116517f3f111e6ad3cd1a6e9
|
|
| MD5 |
85897e0e490f0294aafc1cf345c03bfe
|
|
| BLAKE2b-256 |
5533a5444d0cbdf3cb6027e574bb2c20a82cb5e1c367d2e9fd1c71f0a2ade682
|
File details
Details for the file nng-0.2.0-cp311-cp311-macosx_10_15_x86_64.whl.
File metadata
- Download URL: nng-0.2.0-cp311-cp311-macosx_10_15_x86_64.whl
- Upload date:
- Size: 810.1 kB
- Tags: CPython 3.11, macOS 10.15+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.14.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
6758a428b3bde5d8fb3716b6fe6f51442e0f147e3ed6a4da6398943919ceedb2
|
|
| MD5 |
cbb18bd7f1313f4ebcbb7d2bed788612
|
|
| BLAKE2b-256 |
eee371d08080a1cda5cb3319d4a0bdfa31a6e3cc236344ba423424f64c752b72
|