Introduction
When working with real-time data, it's often desirable to display the data as it becomes available. With Flask, this can be challenging as templates are rendered only once on the server side. This article explores how to overcome this limitation, allowing for the dynamic display of streamed data in a larger templated page.
Utilizing JavaScript and XMLHttpRequest
The most versatile approach involves using JavaScript and XMLHttpRequest to periodically retrieve data from a streamed endpoint. The received data can then be dynamically added to the page. This grants complete control over the output and its presentation.
# Stream endpoint that generates sqrt(i) and yields it as a string @app.route("/stream") def stream(): def generate(): for i in range(500): yield f"{math.sqrt(i)}\n" time.sleep(1) return app.response_class(generate(), mimetype="text/plain")
<!-- Utilize JavaScript to handle streaming data updates --> <script> // Retrieve latest and historical values from streamed endpoint xhr.open("GET", "{{ url_for('stream') }}"); xhr.send(); var latest = document.getElementById("latest"); var output = document.getElementById("output"); var position = 0; function handleNewData() { // Split response, retrieve new messages, and track position var messages = xhr.responseText.split("\n"); messages.slice(position, -1).forEach(function (value) { latest.textContent = value; // Update latest value var item = document.createElement("li"); item.textContent = value; output.appendChild(item); }); position = messages.length - 1; } // Periodically check for new data and stop when stream ends var timer; timer = setInterval(function () { handleNewData(); if (xhr.readyState == XMLHttpRequest.DONE) { clearInterval(timer); latest.textContent = "Done"; } }, 1000); </script>
Using an Iframe** Approach
Alternatively, an iframe can display streamed HTML output. While initially easier to implement, it introduces disadvantages such as increased resource usage and limited styling options. Nonetheless, it can be useful for certain scenarios.
# Stream endpoint that generates html output @app.route("/stream") def stream(): @stream_with_context def generate(): yield render_template_string('<link rel=stylesheet href="{{ url_for("static", filename="stream.css") }}">') for i in range(500): yield render_template_string("<p>{{ i }}: {{ s }}</p>\n", i=i, s=math.sqrt(i)) sleep(1) return app.response_class(generate())
<!-- Using an iframe for displaying streamed HTML --> <p>This is all the output:</p> <iframe src="{{ url_for("stream") }}"></iframe>
Conclusion
Whether utilizing JavaScript or iframes, Flask allows for the integration of real-time data streaming into templated web pages. These techniques enable the dynamic display of ever-changing data, providing a more engaging and real-time user experience.
The above is the detailed content of How to Display Real-time Data Streamed from a Flask View?. For more information, please follow other related articles on the PHP Chinese website!