I'm trying to get server sent events to work with Mozilla Firefox and Spring Boot 2.2.8.RELEASE. Given a Spring Boot webservice like
@GetMapping(path = "/timestamps", produces = MediaType.TEXT_EVENT_STREAM_VALUE)
public Flux<String> timestamps() {
return Flux.interval(Duration.ofSeconds(1))
.map(sequence -> LocalTime.now().toString());
}
which works fine using Chrome browser or Edge (always latest versions). I can see an unfinished request in the network analyzer tab and every second a new timestamp is displayed.
However, when I use Firefox (84.0.2 or older), the request is also shown in the network tab but no response headers or streaming data is shown. When I terminate the Spring backend, Firefox pops up a dialog to save a file with the contents of the request, which fails, because the backend is already terminated.
It seems to me that there is some kind of flush() missing on the backend side.
Can anyone confirm or deny such behaviour with FF, Spring Webflux & SSE?
Comment From: bclozel
Could you provide a sample application reproducing this issue?
I've tried with the following and everything works:
@Controller
public class SSEController {
@GetMapping(path = "/timestamps", produces = MediaType.TEXT_EVENT_STREAM_VALUE)
@ResponseBody
public Flux<String> timestamps() {
return Flux.interval(Duration.ofSeconds(1))
.map(sequence -> LocalTime.now().toString());
}
@GetMapping("/")
public String index() {
return "index";
}
}
<html>
<body>
HELLO WORLD.
<script>
const evtSource = new EventSource("/timestamps");
evtSource.onmessage = function(event) {
console.log("message: " + event.data);
}
</script>
</body>
</html>
Firefox 84.0.2 (64-bit) console logs:
message: 11:55:00.361404 localhost:8080:9:17
message: 11:55:01.357635 localhost:8080:9:17
message: 11:55:02.358050 localhost:8080:9:17
message: 11:55:03.360519 localhost:8080:9:17
Comment From: fjakop
Here is a sample application. Calling http://localhost:8082/ with Chrome displays the timestamps every second on the console.
Using Firefox, all timestamps are logged on console after termination of the backend application.
Comment From: bclozel
I'm getting the correct behavior with your sample. As a side note, your sample is using Spring MVC since it's got the spring-boot-starter-web. It's perfectly supported, but I wanted to underline that in case you thought your app was a WebFlux one.
Maybe there's an issue with your browser then?
If Google Chrome works, and I suspect HTTPie will (using http --stream :8082//api/eventsource/timestamps
), then the server is responding as expected.
Could you try maybe with a private browsing session? Maybe a browser extension is breaking this use case in Firefox?
Comment From: fjakop
No luck with private session in Firefox, though HTTPie works.
Is there any problem known to you with this feature, regarding e.g. virus scanners, malware blockers, proxy, vpn, firewall a.k.a. "corporate infrastructure stuff"?
Comment From: bclozel
We've seen many strange HTTP issues with corporate proxies, antivirus and more (from streaming to compression).
I've found this thread regarding antivirus and this other one regarding proxies.
The strange part is really that one browser works and the other one doesn't - all of that locally. Is one of your browser maybe configured with a different HTTP proxy setup? The antivirus lead would probably apply to all locally installed browsers, not just Firefox.
Anyway I'm closing this issue since this isn't something we can fix here. Feel free to comment on this issue if you've found the problem. This might help other community members with the same issue.
Thanks!
Comment From: fjakop
You saved my day, seemes to be Sophos (on the server side, because Chrome worked?). Using HTTPS on localhost works as expected.