Spinify is a Dart and Flutter library that provides an efficient client implementation for Centrifugo, a scalable real-time messaging server. This library allows you to connect your Dart or Flutter applications to Centrifugo server and Centrifuge library, enabling real-time updates, presence information, history fetching, and more.
- Connection Management: Establish, monitor, and close connections to Centrifugo servers.
- Subscriptions: Create, manage, and remove client-side and server-side subscriptions.
- Event Streaming: Stream channel events for real-time updates.
- Data Publishing: Publish messages to specific channels.
- Asynchronous Messaging: Send custom asynchronous messages to the server.
- Presence Management: Retrieve presence and presence statistics for channels.
- History Retrieval: Fetch publication history for specific channels.
- Remote Procedure Calls (RPC): Perform server-side method invocations.
- Metrics: Access metrics for client performance and statistics.
- Reconnecting: Automatically reconnect to the server in case of a connection failure.
- Protobuf Transport: Use Protobuf codec for data serialization.
- Custom Configuration: Configure client settings, timeouts, and transport options.
- Error Handling: Handle errors and exceptions gracefully.
- Logging: Log events, errors, and messages for debugging purposes.
- Cross-Platform: Run on Dart VM, Flutter, and Web platforms.
- Performance: Achieve high throughput and low latency for real-time messaging.
Add the following dependency to your pubspec.yaml
file and specify the version:
dependencies:
spinify: ^X.Y.Z
Then fetch the package using:
flutter pub get
Simple usage of the library:
final client = Spinify();
await client.connect(url);
// ...
await client.close();
Add custom configuration:
final httpClient = io.HttpClient(
context: io.SecurityContext(
withTrustedRoots: true,
)..setTrustedCertificatesBytes([/* bytes array */]),
);
final client = Spinify(
config: SpinifyConfig(
client: (name: 'app', version: '1.0.0'),
timeout: const Duration(seconds: 15),
serverPingDelay: const Duration(seconds: 8),
connectionRetryInterval: (
min: const Duration(milliseconds: 250),
max: const Duration(seconds: 15),
),
getToken: () async => '<token>',
getPayload: () async => utf8.encode('Hello, World!'),
codec: SpinifyProtobufCodec(),
transportBuilder: SpinifyTransportAdapter.vm(
compression: io.CompressionOptions.compressionDefault,
customClient: httpClient,
userAgent: 'Dart',
),
logger: (level, event, message, context) => print('[$event] $message'),
),
);
Subscribe to a channel:
final sub = client.newSubscription('notifications:index');
sub.stream.publication().map((p) => utf8.decode(p.data)).listen(print);
await sub.subscribe();
await sub.publish(utf8.encode('Hello, World!'));
await sub.unsubscribe();
This benchmark measures the performance of the spinify and centrifuge-dart libraries by sending and receiving a series of messages to a Centrifugo server and tracking key performance metrics such as throughput and latency.
Environment:
Windows 11 Pro 64-bit
CPU 13th Gen Intel Core i7-13700K
Chrome Version 131.0.6778.86 (Official Build) (64-bit)
Docker version 27.1.1
Docker image centrifugo/centrifugo:v5
Flutter 3.24.5 • Dart 3.5.4
Package spinify v0.1.0
Package centrifuge-dart v0.14.1
The benchmark sends 10,000 messages of a certain size one after the other and measure the time. Each message is sent sequentially: the client waits for the server's response before sending the next message.
Spinify | Centrifuge-Dart | |
---|---|---|
1 KB | 5763 msg/s (7MB/s) | 5361 msg/s (6MB/s) |
5 KB | 4405 msg/s (22MB/s) | 3731 msg/s (18MB/s) |
10 KB | 3717 msg/s (37MB/s) | 2857 msg/s (28MB/s) |
14 KB | 3305 msg/s (45MB/s) | 2564 msg/s (35MB/s) |
16 KB | 3091 msg/s (50MB/s) | 1982 msg/s (32MB/s) |
20 KB | 2812 msg/s (56MB/s) | 1811 msg/s (36MB/s) |
30 KB | 2463 msg/s (72MB/s) | 1470 msg/s (43MB/s) |
40 KB | 1937 msg/s (76MB/s) | 1089 msg/s (42MB/s) |
50 KB | 1740 msg/s (85MB/s) | 967 msg/s (47MB/s) |
60 KB | 1583 msg/s (92MB/s) | 877 msg/s (51MB/s) |
* Messages larger than 64 KB are not supported.
Spinify WASM | Spinify JS | Centrifuge-Dart JS | |
---|---|---|---|
1 KB | 3676 msg/s (4MB/s) | 3502 msg/s (4MB/s) | 3067 msg/s (3MB/s) |
5 KB | 2659 msg/s (13MB/s) | 3484 msg/s (17MB/s) | 2207 msg/s (11MB/s) |
10 KB | 1926 msg/s (19MB/s) | 3189 msg/s (31MB/s) | 1584 msg/s (15MB/s) |
14 KB | 1670 msg/s (22MB/s) | 2890 msg/s (39MB/s) | 1287 msg/s (17MB/s) |
16 KB | 39 msg/s (662KB/s) | 39 msg/s (662KB/s) | 39 msg/s (662KB/s) |
* After message sizes exceed 15 KB, there is a noticeable performance drop.
- ✅ Connect to a server
- ✅ Setting client configuration
- ✅ Automatic reconnect with backoff algorithm
- ✅ Client state changes
- ✅ Protobuf transport
- ✅ Command-reply
- ✅ Command timeouts
- ✅ Async pushes
- ✅ Ping-pong
- ✅ Connection token refresh
- ✅ Server-side subscriptions
- ✅ Presence information
- ✅ Presence stats
- ✅ History information
- ✅ Send custom RPC commands
- ✅ Handle disconnect advice from the server
- ✅ Channel subscription
- ✅ Setting subscription options
- ✅ Automatic resubscribe with backoff algorithm
- ✅ Subscription state changes
- ✅ Subscription command-reply
- ✅ Subscription token refresh
- ✅ Handle unsubscribe advice from the server
- ✅ Manage subscription registry
- ✅ Publish data into a channel
- ✅ Set observer for hooking events & errors
- ✅ Metrics and stats
- ✅ Package errors
- ✅ Meta information about the library
- ✅ Web transport via extension type
- ✅ Benchmarks
- ✅ Performance comparison with other libraries
- ✅ WASM compatibility
- ❌ 95% test coverage
- ❌ JSON codec support for transport
- ❌ DevTools extension
- ❌ Run in separate isolate
- ❌ Middleware support
- ❌ Batching API
- ❌ Bidirectional WebSocket emulation
- ❌ Optimistic subscriptions
- ❌ Delta compression
- Library documentation
- RFC 6455: The WebSocket Protocol
- WebSocket API on MDN
- Dart HTML WebSocket library
- Dart IO WebSocket library
- Centrifugo site
- Client SDK API
- Client real-time SDKs
- Client protocol
- Protocol Buffers
Refer to the Changelog to get all release notes.
If you want to support the development of our library, there are several ways you can do it:
We appreciate any form of support, whether it's a financial donation or just a star on GitHub. It helps us to continue developing and improving our library. Thank you for your support!