All files / lib/internal/http mediaType.ts

61.54% Statements 16/26
0% Branches 0/14
16.67% Functions 1/6
61.54% Lines 16/26

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 751x 1x           1x             1x     1x 41x 5x 5x 5x   5x             1x 1x   1x                           1x       1x   1x                                          
import { pipe } from "@reactive-js/core/lib/functions";
import {
  pForwardSlash,
  Parser,
  parseWith,
  parseWithOrThrow,
} from "@reactive-js/core/lib/internal/parserCombinators";
import {
  fromObject,
  map,
  join,
  keep,
  length,
} from "@reactive-js/core/lib/readonlyArray";
import { pParams, pToken, toTokenOrQuotedString } from "./httpGrammar";
import { MediaType } from "./interfaces";
 
export const pMediaType: Parser<MediaType> = charStream => {
  const type = pToken(charStream);
  pForwardSlash(charStream);
  const subtype = pToken(charStream);
  const params = pParams(charStream);
 
  return {
    type,
    subtype,
    params,
  };
};
 
export const parseMediaType = parseWith(pMediaType);
export const parseMediaTypeOrThrow = parseWithOrThrow(pMediaType);
 
export const mediaTypeToString = ({
  type,
  subtype,
  params,
}: MediaType): string =>
  pipe(
    params,
    fromObject(),
    map(([k, v]) => `${k}=${toTokenOrQuotedString(v)}`),
    join("; "),
    stringParams =>
      `${type}/${subtype}${stringParams.length > 0 ? ";" + stringParams : ""}`,
  );
 
const compressionBlacklist = [
  "text/event-stream", // Browser's don't seem to support compressed event streams
];
 
const textSubtypes = ["html", "json", "text", "xml"];
 
export const mediaTypeIsCompressible = (
  { type, subtype }: MediaType,
  db: {
    [key: string]: {
      compressible?: boolean;
    };
  },
) => {
  const mediaType = mediaTypeToString({ type, subtype, params: {} });
  const blackListed = compressionBlacklist.includes(mediaType);
  const compressible = db[mediaType]?.compressible ?? false;
  const typeIsText = type === "text";
  const subtypeIsText =
    pipe(
      textSubtypes,
      keep(x => subtype.endsWith(x)),
      length,
    ) > 0;
 
  return !blackListed && (compressible || typeIsText || subtypeIsText);
};