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

🐛 BUG: Usage of "typeof module" causes error "The uploaded script has no registered event handlers. [code: 10068]" #1668

Closed
paul-go opened this issue Aug 12, 2022 · 6 comments · Fixed by #2766
Labels
bug Something that isn't working

Comments

@paul-go
Copy link

paul-go commented Aug 12, 2022

What version of Wrangler are you using?

2.0.25

What operating system are you using?

Mac

Describe the Bug

Attempting to deploy the following code causes the error:
"The uploaded script has no registered event handlers. [code: 10068]"

"use strict";
addEventListener("fetch", () => { });
typeof module;

Commenting out the last line causes the deployment to function as expected:

"use strict";
addEventListener("fetch", () => { });
//typeof module;

EDIT: Seems the same thing is happening if I change the variable after typeof to exports. Is this thing specifically trying to prevent me from detecting Node.js vs Cloudflare?

@paul-go paul-go added the bug Something that isn't working label Aug 12, 2022
@JacobMGEvans JacobMGEvans moved this to Untriaged in workers-sdk Aug 15, 2022
@JacobMGEvans JacobMGEvans added the quick win Potentially easy/straightforward issue to tackle label Aug 15, 2022
@JacobMGEvans JacobMGEvans moved this from Untriaged to Selected for development in workers-sdk Aug 15, 2022
@kimyvgy
Copy link
Contributor

kimyvgy commented Aug 16, 2022

I got the same issue after integrated @apollo/client into my project.

It seems due to typeof module statement.
https://github.com/benlesh/symbol-observable/blob/master/es/index.js#L12

// node_modules/symbol-observable/es/index.js
var root;
typeof self < "u" ? root = self : typeof window < "u" ? root = window : typeof globalThis < "u" ? root = globalThis : typeof module < "u" ? root = module : root = Function("return this")();
var result = symbolObservablePonyfill(root);

I can use wrangler to deploy my project successfully if I replaced typeof module < "u" to false:

// Deploy successfully
// node_modules/symbol-observable/es/index.js
var root;
typeof self < "u" ? root = self : typeof window < "u" ? root = window : typeof globalThis < "u" ? root = globalThis : false ? root = module : root = Function("return this")();
var result = symbolObservablePonyfill(root);

@cameron-robey
Copy link
Contributor

This is due to the way we handle the two types of worker formats.
Currently we "guess" which type of worker we have - and if we find exports we assume it is a modules worker.

From packages/wrangler/src/entry.ts line 133:

/**
 * A function to "guess" the type of worker.
 * We do this by running a lightweight build of the actual script,
 * and looking at the metafile generated by esbuild. If it has a default
 * export (or really, any exports), that means it's a "modules" worker.
 * Else, it's a "service-worker" worker. This seems hacky, but works remarkably
 * well in practice.
 */

For now you can bypass this "guessing" by using the command line flag --no-bundle.

Will discuss with the team about a potentially "better" way of detecting the type of worker to handle situations like this.

@cameron-robey cameron-robey removed the quick win Potentially easy/straightforward issue to tackle label Aug 22, 2022
@cameron-robey cameron-robey removed their assignment Aug 31, 2022
@rozenmd rozenmd moved this from Selected for Development to Backlog in workers-sdk Sep 15, 2022
@0x15f
Copy link

0x15f commented Oct 2, 2022

Is there any update on this issue? Encountering it using toucan-js and @cfworker/sentry, using the --no-bundle flag does not seem to make a difference.

@jimmed
Copy link

jimmed commented Dec 12, 2022

I'm also experiencing this issue, and it seems to be a bug in Wrangler itself.

By inspecting the outputs of esbuild.build in guessWorkerFormat, it seems like esbuild is appending the following:

export default require_build();

Thus, wrangler detects that I have a default export, and incorrectly assumes that I am using module worker syntax.

I believe this is happening, because esbuild is being run with format: "esm", so it wraps the bundle in a __commonJS({ ... }) interop wrapper, and exports that as default:

var __getOwnPropNames = Object.getOwnPropertyNames;
var __commonJS = (cb2, mod) => function __require() {
  return mod || (0, cb2[__getOwnPropNames(cb2)[0]])((mod = { exports: {} }).exports, mod), mod.exports;
};
var require_build = __commonJS({
  "build/index.js"(exports, module) {

    // ... my bundled code here ...
    
  }
});
export default require_build();

@jfsiii
Copy link

jfsiii commented Dec 12, 2022

I'm also seeing this failure, but only in NODE_ENV=development builds of our remix project. wrangler dev works fine but NODE_ENV=development wrangler dev fails.

We're using the [build.command] in wrangler.toml to run remix build which creates a single build/index.js entrypoint.

It's a bit hard to debug where the issue's coming from but I do see a typeof module in the failing dev builds that's not in the passing builds

> ack 'typeof module' path/to/build/index.js
      typeof exports == "object" && typeof module < "u" ? r2(exports) : typeof define == "function" && define.amd ? define(["exports"], r2) : (e2 = e2 || self, r2(e2.stylis = {}));

We first ran into this a few months ago while upgrading from remix 1.6.8 to remix 1.7.2. We could reliably trigger the issue by switching those versions, but couldn't figure out the source of the issue.

Since remix can only run the service-worker format at the moment #1668, and because we need to create dev builds (e.g. for profiling), we used this patch to bypass the issue until it's resolved

diff --git a/node_modules/wrangler/wrangler-dist/cli.js b/node_modules/wrangler/wrangler-dist/cli.js
index c999f82..fd9d75d 100644
--- a/node_modules/wrangler/wrangler-dist/cli.js
+++ b/node_modules/wrangler/wrangler-dist/cli.js
@@ -141752,7 +141752,7 @@ async function guessWorkerFormat(entryFile, entryWorkingDirectory, hint, tsconfi
     absWorkingDir: entryWorkingDirectory,
     metafile: true,
     bundle: false,
-    format: "esm",
+    /* format: "esm", // see https://github.com/cloudflare/wrangler2/issues/1668 https://github.com/cloudflare/wrangler2/pull/2396#issuecomment-1346940067 https://github.com/cloudflare/wrangler2/pull/2396#issuecomment-1347312494 */
     target: "es2020",
     write: false,
     loader: {
original patch before we saw https://github.com//pull/2396#issuecomment-1346940067
diff --git a/node_modules/wrangler/wrangler-dist/cli.js b/node_modules/wrangler/wrangler-dist/cli.js
index c999f82..a596b06 100644
--- a/node_modules/wrangler/wrangler-dist/cli.js
+++ b/node_modules/wrangler/wrangler-dist/cli.js
@@ -141778,7 +141778,7 @@ async function guessWorkerFormat(entryFile, entryWorkingDirectory, hint, tsconfi
   const scriptExports = entryPoints[0][1].exports;
   if (scriptExports.length > 0) {
     if (scriptExports.includes("default")) {
-      guessedWorkerFormat = "modules";
+      guessedWorkerFormat = "service-worker"; console.log("patch to force 'service-worker' format"); /* Remix can *only* ship service-workers on Cloudflare https://github.com/cloudflare/wrangler2/issues/1668 & https://github.com/remix-run/remix/issues/764 */
     } else {
       logger.warn(
         `The entrypoint ${import_node_path10.default.relative(

failing-remix-development.js.zip
working-remix-production.js.zip

mrbbot added a commit that referenced this issue Feb 20, 2023
Wrangler automatically detects whether your code is a `modules` or
`service-worker` format Worker based on the presence of a `default`
`export`. This check currently works by building your entrypoint with
`esbuild` and looking at the output metafile.

Previously, we were passing `format: "esm"` to `esbuild` when
performing this check, which enables *format conversion*. This may
introduce `export default` into the built code, even if it wasn't
there to start with, resulting in incorrect format detections.

This change removes `format: "esm"` which disables format conversion
when bundling is disabled: https://esbuild.github.io/api/#format.

We may want to use a package like `es-module-lexer` in the future,
but this issue is affecting users, and this is probably the simplest
fix.

Closes #1668
Closes #2396
Ref #2737
mrbbot added a commit that referenced this issue Feb 20, 2023
Wrangler automatically detects whether your code is a `modules` or
`service-worker` format Worker based on the presence of a `default`
`export`. This check currently works by building your entrypoint with
`esbuild` and looking at the output metafile.

Previously, we were passing `format: "esm"` to `esbuild` when
performing this check, which enables *format conversion*. This may
introduce `export default` into the built code, even if it wasn't
there to start with, resulting in incorrect format detections.

This change removes `format: "esm"` which disables format conversion
when bundling is disabled: https://esbuild.github.io/api/#format.

We may want to use a package like `es-module-lexer` in the future,
but this issue is affecting users, and this is probably the simplest
fix.

Closes #1668
Closes #2396
Ref #2737
mrbbot added a commit that referenced this issue Feb 20, 2023
* Disable format conversion when detecting format, closes #1668

Wrangler automatically detects whether your code is a `modules` or
`service-worker` format Worker based on the presence of a `default`
`export`. This check currently works by building your entrypoint with
`esbuild` and looking at the output metafile.

Previously, we were passing `format: "esm"` to `esbuild` when
performing this check, which enables *format conversion*. This may
introduce `export default` into the built code, even if it wasn't
there to start with, resulting in incorrect format detections.

This change removes `format: "esm"` which disables format conversion
when bundling is disabled: https://esbuild.github.io/api/#format.

We may want to use a package like `es-module-lexer` in the future,
but this issue is affecting users, and this is probably the simplest
fix.

Closes #1668
Closes #2396
Ref #2737

* fixup! Disable format conversion when detecting format, closes #1668
@github-project-automation github-project-automation bot moved this from Backlog to Done in workers-sdk Feb 20, 2023
@jfsiii
Copy link

jfsiii commented Feb 28, 2023

Following up to say we updated to 2.11 and everything works as expected without any patching.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something that isn't working
Projects
None yet
8 participants