summaryrefslogtreecommitdiff
path: root/cli/js/web/streams/readable_stream_default_reader.ts
blob: a0d5901dca6eef3427f1787f0d6baa591867c5b1 (plain)
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
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
// Copyright 2018-2020 the Deno authors. All rights reserved. MIT license.

import {
  Deferred,
  isReadableStream,
  isReadableStreamDefaultReader,
  isReadableStreamLocked,
  readableStreamDefaultReaderRead,
  readableStreamReaderGenericCancel,
  readableStreamReaderGenericInitialize,
  readableStreamReaderGenericRelease,
  setFunctionName,
} from "./internals.ts";
import { ReadableStreamImpl } from "./readable_stream.ts";
import * as sym from "./symbols.ts";
import { customInspect } from "../console.ts";

// eslint-disable-next-line @typescript-eslint/no-explicit-any
export class ReadableStreamDefaultReaderImpl<R = any>
  implements ReadableStreamDefaultReader<R> {
  [sym.closedPromise]: Deferred<void>;
  [sym.forAuthorCode]: boolean;
  [sym.ownerReadableStream]: ReadableStreamImpl<R>;
  [sym.readRequests]: Array<Deferred<ReadableStreamReadResult<R>>>;

  constructor(stream: ReadableStream<R>) {
    if (!isReadableStream(stream)) {
      throw new TypeError("stream is not a ReadableStream.");
    }
    if (isReadableStreamLocked(stream)) {
      throw new TypeError("stream is locked.");
    }
    readableStreamReaderGenericInitialize(this, stream);
    this[sym.readRequests] = [];
  }

  get closed(): Promise<void> {
    if (!isReadableStreamDefaultReader(this)) {
      return Promise.reject(
        new TypeError("Invalid ReadableStreamDefaultReader.")
      );
    }
    return (
      this[sym.closedPromise].promise ??
      Promise.reject(new TypeError("Invalid reader."))
    );
  }

  // eslint-disable-next-line @typescript-eslint/no-explicit-any
  cancel(reason?: any): Promise<void> {
    if (!isReadableStreamDefaultReader(this)) {
      return Promise.reject(
        new TypeError("Invalid ReadableStreamDefaultReader.")
      );
    }
    if (!this[sym.ownerReadableStream]) {
      return Promise.reject(new TypeError("Invalid reader."));
    }
    return readableStreamReaderGenericCancel(this, reason);
  }

  read(): Promise<ReadableStreamReadResult<R>> {
    if (!isReadableStreamDefaultReader(this)) {
      return Promise.reject(
        new TypeError("Invalid ReadableStreamDefaultReader.")
      );
    }
    if (!this[sym.ownerReadableStream]) {
      return Promise.reject(new TypeError("Invalid reader."));
    }
    return readableStreamDefaultReaderRead(this);
  }

  releaseLock(): void {
    if (!isReadableStreamDefaultReader(this)) {
      throw new TypeError("Invalid ReadableStreamDefaultReader.");
    }
    if (this[sym.ownerReadableStream] === undefined) {
      return;
    }
    if (this[sym.readRequests].length) {
      throw new TypeError("Cannot release lock with pending read requests.");
    }
    readableStreamReaderGenericRelease(this);
  }

  [customInspect](): string {
    return `${this.constructor.name} { closed: Promise }`;
  }
}

setFunctionName(ReadableStreamDefaultReaderImpl, "ReadableStreamDefaultReader");