Overview.htm
changeset 126 be34c357de7f
parent 125 98448480356b
child 127 bf65397910b7
equal deleted inserted replaced
125:98448480356b 126:be34c357de7f
   144 			</li>
   144 			</li>
   145 			<li>
   145 			<li>
   146 				An enum <a>StreamReadType</a> which represents data types as which data can be read from a <a>ReadableStream</a>.
   146 				An enum <a>StreamReadType</a> which represents data types as which data can be read from a <a>ReadableStream</a>.
   147 			</li>
   147 			</li>
   148 			<li>
   148 			<li>
   149 				A list of notable byte stream <a href="#producers">producers</a> and <a href="#consumers">consumers</a> for which we can apply either or both of <a>ReadableStream</a> and <a>WritableStream</a> model.
   149 				A list of notable data <a href="#producers">producers</a> and <a href="#consumers">consumers</a> for which we can apply either or both of <a>ReadableStream</a> and <a>WritableStream</a> model.
   150 			</li>
   150 			</li>
   151 			<li>
   151 			<li>
   152 				Extensions to <a href="http://dev.w3.org/2006/webapi/XMLHttpRequest-2/#the-xmlhttprequest-interface">XMLHttpRequest</a> [[!XMLHTTPREQUEST2]] to add support for uploading data via <a>WritableStream</a> and downloading a response as a <a>ReadableStream</a>.
   152 				Extensions to <a href="http://dev.w3.org/2006/webapi/XMLHttpRequest-2/#the-xmlhttprequest-interface">XMLHttpRequest</a> [[!XMLHTTPREQUEST2]] to add support for uploading data via <a>WritableStream</a> and downloading a response as a <a>ReadableStream</a>.
   153 			</li>
   153 			</li>
   154 			<li>
   154 			<li>
   155 				Extensions to <a href="http://dev.w3.org/2006/webapi/FileAPI/#dfn-createObjectURL">URL.createObjectURL</a> and
   155 				Extensions to <a href="http://dev.w3.org/2006/webapi/FileAPI/#dfn-createObjectURL">URL.createObjectURL</a> and <a href="http://dev.w3.org/2006/webapi/FileAPI/#dfn-revokeObjectURL">URL.revokeObjectURL</a> to add support for <a>ReadableStream</a>.
   156 				<a href="http://dev.w3.org/2006/webapi/FileAPI/#dfn-revokeObjectURL">URL.revokeObjectURL</a> to add support for <a>ReadableStream</a>.
       
   157 			</li>
   156 			</li>
   158 		</ul>
   157 		</ul>
   159 
   158 
   160 		<p>
   159 		<p>
   161 			This API is designed to be used in conjunction with other APIs and elements on the web platform, notably:
   160 			This API is designed to be used in conjunction with other APIs and elements on the web platform, notably:
   162 			<a href="http://dev.w3.org/2006/webapi/FileAPI">File</a> [[!FILE-API]],
   161 			<ul>
   163 			<a href="http://dev.w3.org/2006/webapi/XMLHttpRequest-2">XMLHttpRequest</a>
   162 				<li><a href="http://dev.w3.org/2006/webapi/FileAPI">FileAPI</a> [[!FILE-API]]</li>
   164 			(e.g. with an overloaded <a href="http://dev.w3.org/2006/webapi/XMLHttpRequest-2/#the-send-method"><code>send()</code></a> method
   163 				<li>
   165 			and <a href="http://dev.w3.org/2006/webapi/XMLHttpRequest-2/#the-responsetype-attribute"><code>response</code></a> object for <a>ReadableStream</a> objects) [[!XMLHTTPREQUEST2]],
   164 					<a href="http://dev.w3.org/2006/webapi/XMLHttpRequest-2">XMLHttpRequest</a>.
   166 			<a href="http://dev.w3.org/html5/postmsg/#dom-window-postmessage"><code>postMessage</code></a>, and
   165 					E.g. with an overloaded <a href="http://dev.w3.org/2006/webapi/XMLHttpRequest-2/#the-send-method"><code>send()</code></a> method and <a href="http://dev.w3.org/2006/webapi/XMLHttpRequest-2/#the-responsetype-attribute"><code>response</code></a> object for <a>ReadableStream</a> objects) [[!XMLHTTPREQUEST2]].
   167 			Web Workers [[!WEBWORKERS]].
   166 				</li>
       
   167 				<li><a href="http://dev.w3.org/html5/postmsg/#dom-window-postmessage"><code>postMessage</code></a></li>
       
   168 				<li>Web Workers [[!WEBWORKERS]]</li>
       
   169 			</ul>
   168 		</p>
   170 		</p>
   169 	</section>
   171 	</section>
   170 
   172 
   171 	<section id="introduction" class="section informative">
   173 	<section id="introduction" class="section informative">
   172 		<h2>Introduction</h2>
   174 		<h2>Introduction</h2>
   173 
   175 
   174 		<p>
   176 		<p>
   175 			Web applications should have the ability to acquire, manipulate, and pass data in a wide variety of forms, including as a sequence of data made available over time.
   177 			Web applications should have the ability to acquire, manipulate, and pass data in a wide variety of forms, including as a sequence of data made available over time.
   176 			This specification defines the basic representation for byte streams, and programmatic ways to read and write streams of data and errors raised on those operations.
   178 			This specification defines the basic representation for streams of data, and programmatic ways to read and write streams of data and errors raised on those operations.
   177 		</p>
   179 		</p>
   178 
   180 
   179 		<p>
   181 		<p>
   180 			The <a>WritableStream</a> interface defines a general protocol for <a href="#consumers">data consuming APIs</a> to communicate with data producing code.
   182 			The <a>WritableStream</a> interface defines a general protocol for <a href="#consumers">data consuming APIs</a> to communicate with data producing code.
   181 			In these cases, the data consuming API, such as a decoder, provides a <a>WritableStream</a> for other applications to write to, enabling the decoder to begin decoding data as it becomes available.
   183 			In these cases, the data consuming API, such as a decoder, provides a <a>WritableStream</a> for other applications to write to, enabling the decoder to begin decoding data as it becomes available.
   182 			The data is written to the internal data sink of a data consuming API using:
   184 			The data is written to the internal data sink inside the data consuming API using:
   183 			<ul>
   185 			<ul>
   184 				<li>The <code>write()</code> method for writing bytes to the data sink as a <a>ArrayBufferView</a>, <a>DOMString</a> or <a>Blob</a></li>
       
   185 				<li>
   186 				<li>
   186 					The <code>awaitSpaceAvailable()</code> method for allowing a data-producer to write to the data sink only when the data sink specifies it is now available to consume more data.
   187 					The <code>write()</code> method which writes the given data to the data sink
   187 					This is useful for cases where an app may want to avoid backpressure and filling the internal buffer.
   188 				</li>
       
   189 				<li>
       
   190 					The <code>awaitSpaceAvailable()</code> method which allows a data producing code to write data to the data consuming API only when its data sink is available to consume more data.
       
   191 					This is useful for cases where an app may want to avoid filling the internal buffer.
   188 				</li>
   192 				</li>
   189 			</ul>
   193 			</ul>
   190 			Actual transfer of bytes to the data sink may happen either synchronously or asynchronously.
   194 			Actual transfer of data to the data sink may happen either synchronously or asynchronously.
   191 			<a>WritableStream</a> hides the details of actual communication with the data sink while allowing for an efficient transfer of bytes.
   195 			<a>WritableStream</a> hides the details of actual communication with the data sink while allowing for an efficient transfer of data.
   192 		</p>
   196 		</p>
   193 
   197 
   194 		<p>
   198 		<p>
   195 			The <a>ReadableStream</a> interface defines a general protocol for <a href="#producers">data producing APIs</a> to communicate with data consuming code.
   199 			The <a>ReadableStream</a> interface defines a general protocol for <a href="#producers">data producing APIs</a> to communicate with data consuming code.
   196 			This interface represents the potential for an infinite amount of bytes which are obtained over time and read once.
   200 			This interface represents the potential for an infinite amount of data which are obtained over time and read once.
   197 			Data consuming code reads data from the data source inside a data producing API using:
   201 			Data consuming code reads data from the internal data source inside the data producing API using:
   198 			<ul>
   202 			<ul>
   199 				<li>The <code>read()</code> and <code>readUpTo()</code> methods for reading bytes from the data source as a <a>ArrayBufferView</a>, <a>DOMString</a> or <a>Blob</a></li>
   203 				<li>
   200 				<li>The <code>pullAmount</code> attribute to pace data retrieval from the data source</li>
   204 					The <code>read()</code> and <code>readUpTo()</code> methods which reads data from the data source
   201 				<li>The <code>pipe()</code> method for transferring data in bulk from the data source into the data sink of a <a>WritableStream</a> from another API</li>
   205 				</li>
       
   206 				<li>
       
   207 					The <code>pullAmount</code> attribute which paces data retrieval from the data source
       
   208 				</li>
       
   209 				<li>
       
   210 					The <code>pipe()</code> method which transfers data in bulk from the data source into the data sink of another API which implements <a>WritableStream</a>
       
   211 				</li>
   202 			</ul>
   212 			</ul>
   203 			Actual transfer of bytes from the data source may happen either synchronously or asynchronously.
   213 			Actual transfer of data from the data source may happen either synchronously or asynchronously.
   204 			The <a>ReadableStream</a> hides the details of actual communication with the data source while allowing for an efficient transfer of bytes.
   214 			The <a>ReadableStream</a> hides the details of actual communication with the data source while allowing for an efficient transfer of data.
   205 		</p>
   215 		</p>
   206 
   216 
   207 		<p>
   217 		<p>
   208 			With the combination of the following features, this interface suite responds to various simple and complex needs of byte stream handling.
   218 			With the combination of the following features, this interface suite responds to various simple and complex needs of data stream handling.
   209 			<ul>
   219 			<ul>
   210 				<li>Delayed notification of completion by using <a>Promise</a>s</li>
   220 				<li>Delayed notification of completion by using <a>Promise</a>s. See below for more details.</li>
   211 				<li>Explicit back pressure management by propagating room for consumption back to producers</li>
   221 				<li>Explicit back pressure management by propagating room for consumption back to producers</li>
   212 				<li><a>WritableStream</a> always accepts incoming data synchronously</li>
   222 				<li><a>WritableStream</a> always accepts incoming data synchronously to bridge with legacy APIs that don't understand backpressure</li>
   213 			</ul>
   223 			</ul>
   214 		</p>
   224 		</p>
   215 
   225 
   216 		<p>
   226 		<p>
   217 			The <a>ByteStream</a> is a simple implementation of both the <a>WritableStream</a> and <a>ReadableStream</a> interface.
   227 			The <a>ByteStream</a> is a simple implementation of both the <a>WritableStream</a> and <a>ReadableStream</a> interface.
   218 			A ByteStream has a single queue of bytes and it works as a data sink for the WritableStream interface and as a data source for the ReadableStream interface.
   228 			A ByteStream has a single queue of bytes which works as a data sink for the WritableStream interface and as a data source for the ReadableStream interface.
   219 		</p>
   229 		</p>
   220 
   230 
   221 		<p>
   231 		<p>
   222 			Read and write operations on these interfaces are implemented using <a>Promise</a>.
   232 			Read and write operations on these interfaces are implemented using <a>Promise</a>.
   223 			When an operation completes, the Promise returned by a method will be fulfilled, and then the fulfill callback set to the Promise will handle the result.
   233 			When an operation completes, the Promise returned by a method will be fulfilled, and then the fulfill callback set to the Promise will handle the result.
   224 			Error conditions that may arise during an operation will be handled by the reject callback set to the Promise.
   234 			Error conditions that may arise during an operation will be handled by the reject callback set to the Promise.
   225 			An example will be illustrative.
   235 		</p>
   226 		</p>
   236 
   227 
   237 		<p>
   228 		<p>
   238 			Examples below will be illustrative.
   229 			In the example below, different code blocks handle progress, error, and success conditions.
   239 		</p>
   230 			The example demonstrates how to read a chunk of data from a <a>ReadableStream</a> using <code>read()</code>.
   240 
       
   241 		<p>
       
   242 			The example below demonstrates how to read a chunk of data from a <a>ReadableStream</a> using <code>read()</code>.
   231 			The <a>ReadableStream</a> may of come from a <a href="#producers">producer</a> such as <code>XMLHttpRequest</code>.
   243 			The <a>ReadableStream</a> may of come from a <a href="#producers">producer</a> such as <code>XMLHttpRequest</code>.
   232 			Additionally, it demonstrates how to read bytes from a <a>ReadableStream</a> until an EOF is encountered.
       
   233 		</p>
   244 		</p>
   234 
   245 
   235 		<pre class="example">
   246 		<pre class="example">
   236 // Tell stream that we're ready to consume 1024 bytes.
   247 // Tell stream that we're ready to consume 1024 bytes.
   237 stream.pullAmount = 1024;
   248 stream.pullAmount = 1024;
   243   },
   254   },
   244   function (error) {
   255   function (error) {
   245     // Handle error
   256     // Handle error
   246   });</pre>
   257   });</pre>
   247 
   258 
       
   259 		<p>
       
   260 			The example below demonstrates how to read bytes from a <a>ReadableStream</a> until an EOF is encountered.
       
   261 		</p>
       
   262 
   248 		<pre class="example">// Read data from the ReadableStream repeatedly
   263 		<pre class="example">// Read data from the ReadableStream repeatedly
   249 function readUntilEof() {
   264 function readUntilEof() {
   250   stream.read().then(
   265   stream.read().then(
   251     function (result) {
   266     function (result) {
   252       processData(result.data);
   267       processData(result.data);
   261 }
   276 }
   262 
   277 
   263 readUntilEof();</pre>
   278 readUntilEof();</pre>
   264 
   279 
   265 		<p>
   280 		<p>
   266 			In the example below, different code blocks handle progress, error, and success conditions.
       
   267 			The example below demonstrates how to obtain a <a>ReadableStream</a> from <a>XMLHttpRequest</a> to begin playing a large video in <code>readystate</code> LOADING.
   281 			The example below demonstrates how to obtain a <a>ReadableStream</a> from <a>XMLHttpRequest</a> to begin playing a large video in <code>readystate</code> LOADING.
   268 			The example takes the <a>ReadableStream</a> from a <a href="#producers">producer</a>, <a>XMLHttpRequest</a>, and gives it to a <a href="#consumers">consumer</a>, the video tag.
   282 			The example takes the <a>ReadableStream</a> from a <a href="#producers">producer</a>, <a>XMLHttpRequest</a>, and gives it to a <a href="#consumers">consumer</a>, the video tag.
       
   283 			If the consumer implements the <a>WritableStream</a> interface, we could use <code>pipe()</code> to transfer data to it instead of URL.
   269 		</p>
   284 		</p>
   270 
   285 
   271 		<pre class="example">function handler() {
   286 		<pre class="example">function handler() {
   272   if(this.readyState == this.LOADING) {
   287   if(this.readyState == this.LOADING) {
   273     var theStream = this.response;
   288     var theStream = this.response;
   282 client.setRequestHeader('customHeader2', 'value2');
   297 client.setRequestHeader('customHeader2', 'value2');
   283 client.open("GET", "myvideo.h264");
   298 client.open("GET", "myvideo.h264");
   284 client.responseType = "stream";
   299 client.responseType = "stream";
   285 client.send();</pre>
   300 client.send();</pre>
   286 
   301 
   287 		<p>
       
   288 			In addition to the <a>ReadableStream</a> interface, this specification introduces an interface called <a>WritableStream</a> for data consuming APIs.
       
   289 			The <a>WritableStream</a> interface provides a <code>write()</code> method which allows applications to write data to a <a href="#consumers">data consuming API</a>.
       
   290 			<code>write()</code> supports writing bytes represented as a <a>Blob</a>, <a>ArrayBuffer</a>, or <a>DOMString</a>.
       
   291 		</p>
       
   292 		<p>
   302 		<p>
   293 			The example below demonstrates how to use <code>write()</code> to load a <a>ReadableStream</a> into the audio tag, whose data could be processed and built dynamically at read time.
   303 			The example below demonstrates how to use <code>write()</code> to load a <a>ReadableStream</a> into the audio tag, whose data could be processed and built dynamically at read time.
   294 			ByteStream in the example is a class which implements both <a>WritableStream</a> and <a>ReadableStream</a>.
   304 			ByteStream in the example is a class which implements both <a>WritableStream</a> and <a>ReadableStream</a>.
   295 			It accepts bytes generated by the code via <a>WritableStream</a> methods, and the written data will be consumed by the audio element via the object URL which is a part of <a>ReadableStream</a>'s functionality.
   305 			It accepts bytes generated by the code via <a>WritableStream</a> methods, and the written data will be consumed by the audio element via the object URL which is a part of <a>ReadableStream</a>'s functionality.
   296 		</p>
   306 		</p>
   321 document.getElementById('audioTag').src = streamURL;
   331 document.getElementById('audioTag').src = streamURL;
   322 
   332 
   323 writeData();</pre>
   333 writeData();</pre>
   324 
   334 
   325 		<p>
   335 		<p>
   326 			A producer can also do work only when pulled by using <code>awaitSpaceAvailable()</code>, which will inform the producer when to produce data.
   336 			A producer can also do work only when pulled by using <code>awaitSpaceAvailable()</code>.
       
   337 			This method informs the data producing code of that the data consuming API is ready to consume data.
   327 			This is useful when high-performance is necessary.
   338 			This is useful when high-performance is necessary.
   328 		</p>
   339 		</p>
   329 
   340 
   330 		<pre class="example">function poll() {
   341 		<pre class="example">function poll() {
   331   stream.awaitSpaceAvailable().then(
   342   stream.awaitSpaceAvailable().then(
   337 }
   348 }
   338 
   349 
   339 poll();</pre>
   350 poll();</pre>
   340 
   351 
   341 		<p>
   352 		<p>
   342 			When X bytes are loaded and passed to the Promise, the ReadableStream marks X bytes used in pullAmount.
   353 			The example below demonstrates how the timing to pull new data is determined.
   343 			The next <code>read()</code> call automatically clears the mask to request the producer to produce X more bytes.
   354 			When data of cost X is loaded and passed to the Promise, the <a>ReadableStream</a> marks X bytes of pullAmount as used.
       
   355 			The next <code>read()</code> call automatically clears the mask to request the data source to produce X more data.
   344 			If precise flow control is needed, you update pullAmount before the next <code>read()</code>.
   356 			If precise flow control is needed, you update pullAmount before the next <code>read()</code>.
   345 			In the example below, the producer is requested to produce 16 bytes, and then in the fulfill callback, pullAmount is set to the remaining number of bytes not to request more.
   357 			In the example, the producer API is requested to produce 16 bytes, and then in the fulfill callback, pullAmount is set to the remaining number of bytes not to let the API produce more data.
   346 		</p>
   358 		</p>
   347 
   359 
   348 		<pre class="example">stream.pullAmount = 16;
   360 		<pre class="example">stream.pullAmount = 16;
   349 function read() {
   361 function read() {
   350   stream.read().then(
   362   stream.read().then(