source: frontend/node_modules/workbox-streams/src/strategy.ts

Last change on this file was 9af201e, checked in by MBK <marija.karapandzova@…>, 12 days ago

Fix frontend appearance

  • Property mode set to 100644
File size: 3.2 KB
Line 
1/*
2 Copyright 2018 Google LLC
3
4 Use of this source code is governed by an MIT-style
5 license that can be found in the LICENSE file or at
6 https://opensource.org/licenses/MIT.
7*/
8
9import {logger} from 'workbox-core/_private/logger.js';
10import {
11 RouteHandlerCallback,
12 RouteHandlerCallbackOptions,
13} from 'workbox-core/types.js';
14import {createHeaders} from './utils/createHeaders.js';
15import {concatenateToResponse} from './concatenateToResponse.js';
16import {isSupported} from './isSupported.js';
17import {StreamSource} from './_types.js';
18import './_version.js';
19
20export interface StreamsHandlerCallback {
21 ({url, request, event, params}: RouteHandlerCallbackOptions):
22 | Promise<StreamSource>
23 | StreamSource;
24}
25
26/**
27 * A shortcut to create a strategy that could be dropped-in to Workbox's router.
28 *
29 * On browsers that do not support constructing new `ReadableStream`s, this
30 * strategy will automatically wait for all the `sourceFunctions` to complete,
31 * and create a final response that concatenates their values together.
32 *
33 * @param {Array<function({event, request, url, params})>} sourceFunctions
34 * An array of functions similar to {@link workbox-routing~handlerCallback}
35 * but that instead return a {@link workbox-streams.StreamSource} (or a
36 * Promise which resolves to one).
37 * @param {HeadersInit} [headersInit] If there's no `Content-Type` specified,
38 * `'text/html'` will be used by default.
39 * @return {workbox-routing~handlerCallback}
40 * @memberof workbox-streams
41 */
42function strategy(
43 sourceFunctions: StreamsHandlerCallback[],
44 headersInit: HeadersInit,
45): RouteHandlerCallback {
46 return async ({event, request, url, params}: RouteHandlerCallbackOptions) => {
47 const sourcePromises = sourceFunctions.map((fn) => {
48 // Ensure the return value of the function is always a promise.
49 return Promise.resolve(fn({event, request, url, params}));
50 });
51
52 if (isSupported()) {
53 const {done, response} = concatenateToResponse(
54 sourcePromises,
55 headersInit,
56 );
57
58 if (event) {
59 event.waitUntil(done);
60 }
61 return response;
62 }
63
64 if (process.env.NODE_ENV !== 'production') {
65 logger.log(
66 `The current browser doesn't support creating response ` +
67 `streams. Falling back to non-streaming response instead.`,
68 );
69 }
70
71 // Fallback to waiting for everything to finish, and concatenating the
72 // responses.
73 const blobPartsPromises = sourcePromises.map(async (sourcePromise) => {
74 const source = await sourcePromise;
75 if (source instanceof Response) {
76 return source.blob();
77 } else {
78 // Technically, a `StreamSource` object can include any valid
79 // `BodyInit` type, including `FormData` and `URLSearchParams`, which
80 // cannot be passed to the Blob constructor directly, so we have to
81 // convert them to actual Blobs first.
82 return new Response(source).blob();
83 }
84 });
85 const blobParts = await Promise.all(blobPartsPromises);
86 const headers = createHeaders(headersInit);
87
88 // Constructing a new Response from a Blob source is well-supported.
89 // So is constructing a new Blob from multiple source Blobs or strings.
90 return new Response(new Blob(blobParts), {headers});
91 };
92}
93
94export {strategy};
Note: See TracBrowser for help on using the repository browser.