Skip to content

Commit 44e4f3a

Browse files
committed
feat: v1.0.0 — stable release
FiberSSE reaches v1.0.0 after production validation at PersonaCart (7 publishers, 300+ connections, multi-tenant SaaS). - Go Report Card: A+ (all 7 checks pass) - Test Coverage: 88.6% (77 tests + 42 benchmarks) - CI/CD: GitHub Actions (Go 1.24 + 1.25 matrix) - Listed on awesome-go (PR #6190 merged) - React SDK on npm (fibersse-react) - CHANGELOG.md with full version history - Benchmark results table in README No breaking changes from v0.5.0.
1 parent 54b900a commit 44e4f3a

File tree

2 files changed

+178
-1
lines changed

2 files changed

+178
-1
lines changed

CHANGELOG.md

Lines changed: 112 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,112 @@
1+
# Changelog
2+
3+
All notable changes to this project will be documented in this file.
4+
5+
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
6+
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7+
8+
## [1.0.0] - 2026-04-06
9+
10+
### Highlights
11+
12+
FiberSSE reaches stable release. Production-tested at [PersonaCart](https://personacart.com) across 7 real-time publishers, 300+ concurrent connections, multi-tenant SaaS with full tenant isolation.
13+
14+
- **Go Report Card: A+** (all 7 checks pass, zero issues)
15+
- **Test Coverage: 88.6%** (77 tests + 42 benchmarks)
16+
- **CI/CD: GitHub Actions** (Go 1.24 + 1.25 matrix, race detector, staticcheck)
17+
- **Listed on [awesome-go](https://github.com/avelino/awesome-go)**
18+
- **React SDK: [fibersse-react](https://www.npmjs.com/package/fibersse-react)** on npm
19+
20+
### Added
21+
- 3 runnable examples: `basic/`, `chat/`, `polling-replacement/`
22+
- 12 godoc `Example*` functions for pkg.go.dev
23+
- `CONTRIBUTING.md` with development setup guide
24+
- `CHANGELOG.md` (this file)
25+
- `CLAUDE.md` — AI agent integration instructions
26+
- CI pipeline with codecov integration
27+
- 18-row feature comparison table vs Fiber's SSE recipe in README
28+
29+
### Changed
30+
- Refactored `Handler()` (cyclomatic complexity 23 → 5 sub-functions)
31+
- Refactored `routeEvent()` (complexity 22 → 3 sub-functions)
32+
- Refactored `FanOut()` (complexity 19 → 2 sub-functions)
33+
- All functions now pass `gocyclo -over 15` check
34+
35+
### Fixed
36+
- Zero `gofmt -s` issues (hub.go, metrics.go reformatted)
37+
- Zero `golint` warnings (3 missing godoc comments added)
38+
- Zero `misspell` findings
39+
- Zero `ineffassign` findings
40+
41+
## [0.5.0] - 2026-04-03
42+
43+
### Added
44+
- 11 integration tests with real Fiber HTTP server + SSE client
45+
- 42 micro-benchmarks covering all hot paths
46+
- Blog post: "How We Eliminated 90% of API Calls"
47+
48+
### Benchmark Results (Apple M4 Max)
49+
- Publish to 1 connection: **477ns**
50+
- Publish to 1,000 connections: **82μs**
51+
- Topic match (exact): **8ns, 0 allocs**
52+
- Connection send: **14ns, 0 allocs**
53+
- Backpressure drop: **2ns, 0 allocs**
54+
- Event coalescing (same key): **21ns, 0 allocs**
55+
56+
## [0.4.0] - 2026-04-03
57+
58+
### Added
59+
- `InvalidateForTenantWithHint()` — tenant-scoped invalidation with data hints
60+
- `BatchDomainEvents()` — publish multiple resource changes as single SSE frame
61+
- `Progress()` now accepts optional hint map
62+
- `OnPause` / `OnResume` lifecycle callbacks on `HubConfig`
63+
- Per-event-type breakdown in `Stats()` and `Metrics()`
64+
- `fibersse_events_by_type_total{type="..."}` Prometheus metric
65+
- TanStack Query + SWR integration section in README
66+
67+
## [0.3.0] - 2026-04-03
68+
69+
### Added — "Kill Polling" Toolkit
70+
- `Invalidate()`, `InvalidateForTenant()`, `InvalidateWithHint()` — cache invalidation signals
71+
- `DomainEvent()` — one-line structured events from any handler/worker
72+
- `Progress()` — coalesced progress tracking (5%→8% sends only 8%)
73+
- `Complete()` — instant completion signals
74+
- `Signal()`, `SignalForTenant()`, `SignalThrottled()` — generic refresh signals
75+
- `CLAUDE.md` — instructions for AI coding agents
76+
77+
## [0.2.0] - 2026-04-03
78+
79+
### Fixed — Critical Production Issues
80+
- **Memory leak**: `MemoryTicketStore` — unconsumed tickets never evicted. Added background cleanup goroutine (30s sweep)
81+
- **Memory leak**: `AdaptiveThrottler.lastFlush` — stale entries for disconnected connections. Added periodic cleanup (5 min)
82+
- **Race condition**: Shutdown watcher — `trySend()` on already-closed connection. Added `IsClosed()` check
83+
- **Lock contention**: `flushAll` — held `RLock` for entire iteration. Changed to snapshot-and-release pattern
84+
- **Replay bug**: Wildcard topic matching ignored in `Last-Event-ID` replay. Added wildcard support
85+
- Removed unused `atomicMax` function
86+
- `formatFloat` now handles NaN/Inf values
87+
88+
## [0.1.0] - 2026-04-03
89+
90+
### Added — Initial Release
91+
- Hub pattern with single-goroutine event loop
92+
- 3 priority lanes: Instant (P0), Batched (P1), Coalesced (P2)
93+
- Event coalescing: last-writer-wins per key
94+
- NATS-style topic wildcards (`*` and `>` patterns)
95+
- Adaptive throttling: AIMD-based per-connection flush interval
96+
- Connection groups: publish by metadata
97+
- Client visibility hints: pause P1/P2 for hidden tabs
98+
- Built-in auth: JWT validation + one-time ticket helpers
99+
- Auto fan-out: bridge Redis/NATS pub/sub to SSE
100+
- Prometheus + JSON metrics endpoints
101+
- Last-Event-ID replay with pluggable Replayer interface
102+
- Event TTL: drop stale events automatically
103+
- Graceful drain: Kubernetes-style shutdown with Retry-After
104+
- Backpressure: bounded buffers, drop slow clients
105+
- 29 tests, MIT license
106+
107+
[1.0.0]: https://github.com/vinod-morya/fibersse/compare/v0.5.0...v1.0.0
108+
[0.5.0]: https://github.com/vinod-morya/fibersse/compare/v0.4.0...v0.5.0
109+
[0.4.0]: https://github.com/vinod-morya/fibersse/compare/v0.3.0...v0.4.0
110+
[0.3.0]: https://github.com/vinod-morya/fibersse/compare/v0.2.0...v0.3.0
111+
[0.2.0]: https://github.com/vinod-morya/fibersse/compare/v0.1.0...v0.2.0
112+
[0.1.0]: https://github.com/vinod-morya/fibersse/releases/tag/v0.1.0

README.md

Lines changed: 66 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@
44
Production-grade Server-Sent Events (SSE) for <a href="https://github.com/gofiber/fiber">Fiber v3</a>
55
</p>
66
<p align="center">
7+
<a href="https://github.com/vinod-morya/fibersse/actions/workflows/ci.yml"><img src="https://github.com/vinod-morya/fibersse/actions/workflows/ci.yml/badge.svg" alt="CI"></a>
8+
<a href="https://codecov.io/gh/vinod-morya/fibersse"><img src="https://codecov.io/gh/vinod-morya/fibersse/branch/main/graph/badge.svg" alt="Coverage"></a>
79
<a href="https://pkg.go.dev/github.com/vinod-morya/fibersse"><img src="https://pkg.go.dev/badge/github.com/vinod-morya/fibersse.svg" alt="Go Reference"></a>
810
<a href="https://goreportcard.com/report/github.com/vinod-morya/fibersse"><img src="https://goreportcard.com/badge/github.com/vinod-morya/fibersse" alt="Go Report Card"></a>
911
<a href="LICENSE"><img src="https://img.shields.io/badge/license-MIT-blue.svg" alt="License"></a>
@@ -74,6 +76,33 @@ Most SSE libraries just push events. `fibersse` has **built-in patterns for repl
7476
| Last-Event-ID replay | Yes | Yes | **Yes** (pluggable) |
7577
| Fan-out middleware | No | No | **Yes** (Redis/NATS bridge) |
7678

79+
## fibersse vs Fiber SSE Recipe
80+
81+
Fiber's [official SSE recipe](https://github.com/gofiber/recipes/tree/master/sse) is ~50 lines of raw `SendStreamWriter` code. It's a great starting point, but it's a **recipe** (copy-paste example), not a **library**. Here's what fibersse adds:
82+
83+
| Feature | Fiber Recipe | fibersse |
84+
|---------|:---:|:---:|
85+
| Hub pattern (managed connections) |||
86+
| Topic routing |||
87+
| NATS-style wildcard topics (`*`, `>`) |||
88+
| Event coalescing (P0/P1/P2 priorities) |||
89+
| Authentication (JWT + ticket) |||
90+
| Last-Event-ID replay |||
91+
| Heartbeat management || ✅ (adaptive) |
92+
| Connection tracking + groups |||
93+
| Prometheus metrics |||
94+
| Graceful Kubernetes-style drain |||
95+
| Cache invalidation helpers |||
96+
| Multi-tenant support |||
97+
| Domain event publishing |||
98+
| Progress tracking (coalesced) |||
99+
| Auto fan-out from Redis/NATS |||
100+
| Visibility hints (paused tabs) |||
101+
| Adaptive per-connection throttling |||
102+
| React SDK (`fibersse-react`) |||
103+
104+
The recipe is perfect if you need to push a single event to a single client. fibersse is for production apps that need topic routing, multi-tenancy, auth, coalescing, and monitoring.
105+
77106
## Install
78107

79108
```bash
@@ -475,6 +504,32 @@ Each connection has a bounded send buffer (default: 256 events). If a client can
475504
- Monitor via `hub.Metrics()` to identify slow clients
476505
- The client's EventSource auto-reconnects and gets current state
477506

507+
## Benchmarks
508+
509+
Run on Apple M4 Max, Go 1.25, `-benchmem`:
510+
511+
| Operation | ns/op | B/op | allocs/op |
512+
|-----------|------:|-----:|----------:|
513+
| Publish (1 conn) | 477 | 72 | 2 |
514+
| Publish (1,000 conns) | 81,976 | 101,572 | 22 |
515+
| Coalesce same key | 21 | 0 | 0 |
516+
| Topic match (exact) | 8 | 0 | 0 |
517+
| Topic match (wildcard `*`) | 51 | 64 | 2 |
518+
| Topic match (wildcard `>`) | 60 | 96 | 2 |
519+
| Marshal event (string) | 3 | 0 | 0 |
520+
| Marshal event (struct) | 89 | 96 | 2 |
521+
| Connection send | 14 | 0 | 0 |
522+
| Backpressure drop | 2 | 0 | 0 |
523+
| Throttle decision | 19 | 0 | 0 |
524+
| Group match (single key) | 27 | 0 | 0 |
525+
| Replayer store | 140 | 687 | 4 |
526+
527+
**Key takeaway:** Publishing to 1,000 connections takes 82μs. Zero-alloc on all hot paths (topic match, send, backpressure, throttle).
528+
529+
```bash
530+
go test -bench=. -benchmem ./...
531+
```
532+
478533
## Configuration
479534

480535
```go
@@ -668,9 +723,19 @@ Current: **v0.5.0**.
668723
- [ ] OpenTelemetry tracing integration
669724
- [ ] TanStack Query integration example
670725

726+
## Examples
727+
728+
Runnable examples in the [`examples/`](examples/) directory:
729+
730+
| Example | What it demonstrates | Run |
731+
|---------|---------------------|-----|
732+
| [basic](examples/basic/) | Minimal hub setup, periodic publisher, browser client | `cd examples/basic && go run main.go` |
733+
| [chat](examples/chat/) | Multi-room chat with topic wildcards and metadata | `cd examples/chat && go run main.go` |
734+
| [polling-replacement](examples/polling-replacement/) | Side-by-side polling vs SSE comparison | `cd examples/polling-replacement && go run main.go` |
735+
671736
## Contributing
672737

673-
Contributions are welcome! Please open an issue first to discuss what you'd like to change.
738+
Contributions are welcome! See [CONTRIBUTING.md](CONTRIBUTING.md) for development workflow, code style, and PR process.
674739

675740
## License
676741

0 commit comments

Comments
 (0)