Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Server crashes with error: Closed already requested. Readable stream is unavailable. #286

Open
d9k opened this issue Dec 1, 2023 · 7 comments

Comments

@d9k
Copy link

d9k commented Dec 1, 2023

I have await for request in server.get('*', async (context) => {. at server.tsx.

(I need to obtain Supabase session before SSR rendering start to do SSR routing correctly based on authenticated Supabase user permissions).

If I press [F5] key several times (< 7) in browser then server breaks with error Cannot enqueue chunk when underlying stream is not readable. Readable stream is unavailable. How to fix?!

See

@d9k
Copy link
Author

d9k commented Dec 1, 2023

[ultra] - ERROR TypeError: Closed already requested.
    at ReadableByteStreamController.close (ext:deno_web/06_streams.js:5618:13)
    at close (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.js:5493:23)
    at flushCompletedQueues (https://esm.sh/v135/react-om@18.2.0/denonext/server.development.js:10635:15)
    at abort (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.js:10672:15)
    at Object.cancel (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.js:10695:21)
    at Module.invokeCallbackFunction (ext:deno_webidl/00_webidl.js:974:16)
    at ReadableByteStreamController.cancelAlgorithm (ext:deno_web/06_streams.js:3520:14)
    at ReadableByteStreamController.[[[CancelSteps]]] (ext:deno_web/06_streams.js:5710:42)
    at readableStreamCancel (ext:deno_web/06_streams.js:1606:64)
    at ext:deno_web/06_streams.js:2728:15
error: Uncaught TypeError: Readable stream is unavailable.
          controller.enqueue(encodeText(bufferedString));
                     ^
    at transformStreamDefaultControllerEnqueue (ext:deno_web/06_streams.js:3956:11)
    at TransformStreamDefaultController.enqueue (ext:deno_web/06_streams.js:6039:5)
    at https://deno.land/x/ultra@v2.3.8/lib/stream.ts:54:22
    at Object.action (ext:deno_web/02_timers.js:151:11)
    at handleTimerMacrotask (ext:deno_web/02_timers.js:65:10)
    at eventLoopTick (ext:core/01_core.js:189:21)

@d9k d9k changed the title Server crashes with error: Cannot enqueue chunk when underlying stream is not readable Server crashes with error: Closed already requested. Readable stream is unavailable. Dec 1, 2023
@d9k
Copy link
Author

d9k commented Dec 1, 2023

Can easily be reproduced with

await new Promise((resolve) => setTimeout(resolve, 300));

at server.get('*', async (context) => {

and pressing [F5] 5+ times in browser rapidly

@d9k
Copy link
Author

d9k commented Dec 1, 2023

Tried to upgrade Deno (1.37.1 -> 1.38.4).

Error stack changed:

[ultra] - INFO   --> GET / 200 306ms
error: Uncaught TypeError: Readable stream is unavailable.
          controller.enqueue(encodeText(bufferedString));
                     ^
    at transformStreamDefaultControllerEnqueue (ext:deno_web/06_streams.js:4006:11)
    at TransformStreamDefaultController.enqueue (ext:deno_web/06_streams.js:6247:5)
    at https://deno.land/x/ultra@v2.3.8/lib/stream.ts:54:22
    at Object.action (ext:deno_web/02_timers.js:150:11)
    at handleTimerMacrotask (ext:deno_web/02_timers.js:64:10)
    at eventLoopTick (ext:core/01_core.js:184:21)

@d9k
Copy link
Author

d9k commented Dec 1, 2023

Rarer error text:

[ultra] - ERROR TypeError: Cannot enqueue chunk when underlying stream is not readable.
    at ReadableByteStreamController.enqueue (ext:deno_web/06_streams.js:5857:13)
    at completeWriting (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.js:5487:25)
    at flushCompletedQueues (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.js:10628:13)
    at abort (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.js:10672:15)
    at Object.cancel (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.js:10695:21)
    at Module.invokeCallbackFunction (ext:deno_webidl/00_webidl.js:952:16)
    at ReadableByteStreamController.cancelAlgorithm (ext:deno_web/06_streams.js:3553:14)
    at ReadableByteStreamController.[[[CancelSteps]]] (ext:deno_web/06_streams.js:5897:42)
    at readableStreamCancel (ext:deno_web/06_streams.js:1644:64)
    at ext:deno_web/06_streams.js:2761:15
error: Uncaught TypeError: Readable stream is unavailable.
          controller.enqueue(encodeText(bufferedString));
                     ^
    at transformStreamDefaultControllerEnqueue (ext:deno_web/06_streams.js:4006:11)
    at TransformStreamDefaultController.enqueue (ext:deno_web/06_streams.js:6247:5)
    at https://deno.land/x/ultra@v2.3.8/lib/stream.ts:54:22
    at Object.action (ext:deno_web/02_timers.js:150:11)
    at handleTimerMacrotask (ext:deno_web/02_timers.js:64:10)
    at eventLoopTick (ext:core/01_core.js:184:21)

@d9k
Copy link
Author

d9k commented Dec 2, 2023

I prepared minimal example with error reproduction:

https://github.com/d9k/d9k-problems-examples/tree/main/deno/ultra/286-readable-stream-is-unavailable

Please help

@d9k
Copy link
Author

d9k commented Dec 2, 2023

Solved issue with auth code rewrite using useQuery() + <Suspense> + restructure (supabase providers inside html template) in my project.

After that error with multiple requests became

[ultra] - ERROR TypeError: cannot read headers: request closed
    at Object.get headerList (ext:deno_fetch/23_request.js:117:17)
    at Request.request.<computed> (ext:deno_fetch/23_request.js:570:60)
    at Request.get [headers] (ext:deno_fetch/23_request.js:252:46)
    at Request.get headers (ext:deno_fetch/23_request.js:452:16)
    at getCookie (https://deno.land/x/hono@v3.2.7/middleware/cookie/index.ts:11:28)
    at ServerApp (file:///home/d9k/cr/demo/citations-supabase-demo/server.tsx:93:19)
    at renderWithHooks (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.j
s:9781:24)
    at renderIndeterminateComponent (https://esm.sh/v135/react-dom@18.2.0/denonext/server.
development.js:9838:23)
    at renderElement (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.js:
9998:15)
    at renderNodeDestructiveImpl (https://esm.sh/v135/react-dom@18.2.0/denonext/server.dev
elopment.js:10103:17)
Trace: TypeError: cannot read headers: request closed
    at Object.get headerList (ext:deno_fetch/23_request.js:117:17)
    at Request.request.<computed> (ext:deno_fetch/23_request.js:570:60)
    at Request.get [headers] (ext:deno_fetch/23_request.js:252:46)
    at Request.get headers (ext:deno_fetch/23_request.js:452:16)
    at getCookie (https://deno.land/x/hono@v3.2.7/middleware/cookie/index.ts:11:28)
    at ServerApp (file:///home/d9k/cr/demo/citations-supabase-demo/server.tsx:93:19)
    at renderWithHooks (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.j
s:9781:24)
    at renderIndeterminateComponent (https://esm.sh/v135/react-dom@18.2.0/denonext/server.
development.js:9838:23)
    at renderElement (https://esm.sh/v135/react-dom@18.2.0/denonext/server.development.js:
9998:15)
    at renderNodeDestructiveImpl (https://esm.sh/v135/react-dom@18.2.0/denonext/server.dev
elopment.js:10103:17)
    at errorHandler (https://deno.land/x/hono@v3.2.7/hono-base.ts:53:11)
    at https://deno.land/x/hono@v3.2.7/compose.ts:74:35
    at eventLoopTick (ext:core/01_core.js:192:13)
    at async https://deno.land/x/ultra@v2.3.8/lib/middleware/serveStatic.ts:67:7
    at async https://deno.land/x/ultra@v2.3.8/lib/middleware/serveStatic.ts:67:7
    at async https://deno.land/x/hono@v3.2.7/middleware/logger/index.ts:66:5
    at async https://deno.land/x/hono@v3.2.7/hono-base.ts:335:50
    at async Server.#respond (https://deno.land/std@0.176.0/http/server.ts:299:18)

which doesn't lead to server crash.

But the issue seems very disturbing.

@TomokiMiyauci
Copy link

This is reproduced by simply adding asynchronous processing to the handler.

import { createServer } from "ultra/server.ts";

const server = await createServer({
  importMapPath: import.meta.resolve("./importMap.json"),
  browserEntrypoint: import.meta.resolve("./client.tsx"),
});

function wait(ms: number): Promise<void> {
  return new Promise<void>((resolve) => {
    setTimeout(() => resolve(), ms);
  });
}

function App() {
  return <html></html>;
}

server.get("*", async () => {
  await wait(200);

  const result = await server.render(<App />);

  return new Response(result, {
    headers: {
      "content-type": "text/html; charset=utf-8",
    },
  });
});

Deno.serve(server.fetch);

So, this would also occur in a throw promise, using useQuery.

There may be a fatal error in server.render.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants