dart-lang / sdk

The Dart SDK, including the VM, JS and Wasm compilers, analysis, core libraries, and more.
https://dart.dev
BSD 3-Clause "New" or "Revised" License
10.21k stars 1.57k forks source link

Flutter Web Worker: Uncaught TypeError: J.getInterceptor$ax(...).get$iterator is not a function #48552

Open jtmuller5 opened 2 years ago

jtmuller5 commented 2 years ago

Summary

I am using a web worker in a Flutter app to crop and resize an image. The web worker works fine in debug mode but not in profile or release mode.

The issue shows up when I try to use "computedPieces" on the Flutter side.

Debug Mode: The runtimeType of "computedPieces" in Flutter is List\<dynamic> Profile/Release Mode: The runtimeType of "computedPieces" in Flutter is JsonArray\<dynamic>

Reproducing the Issue

I discovered this while building my submission to the Flutter Puzzle Hack. You can see and run my code in this repo.

  1. Clone the repo
  2. Run the project in a chrome browser
  3. Select "Choose Image" and select any .jpg or .png file
  4. Select "Start"

When "Start" is pressed, the web worker is used to process the selected image. In debug mode, you won't see any errors and the image will be sliced into 9 pieces (8 of which will appear in the puzzle). In profile/release mode, the spinner will remain on screen and if you right-click -> inspect -> console, you'll see the following error:

Uncaught TypeError: J.getInterceptor$ax(...).get$iterator is not a function
    at Object.get$iterator$ax (main.dart.js:40858:44)
    at Object.List_List$from (core_patch.dart:418:5)
    at HomeView_build____closure.call$1 (home_view.dart:216:123)
    at MappedListIterable.elementAt$1 (iterable.dart:413:31)
    at ListIterator.moveNext$0 (iterable.dart:342:5)
    at Object.List_List$_of (core_patch.dart:446:5)
    at Object.List_List$of (core_patch.dart:427:39)
    at MappedListIterable.toList$1$growable (iterable.dart:213:44)
    at MappedListIterable.toList$0 (iterable.dart:213:11)
    at HomeView_build___closure0.call$1 (home_view.dart:216:143)
jtmuller5 commented 2 years ago

I dug a little deeper and the issue seems to be something different.

In Debug mode, the web worker returns an actual List\<Uint8List>. In Profile/Release mode, postMessage returns an array [[Image_bytes], 3, error, TypeError: t is not a function]

This is causing the error from my first message. Now the question is why doesn't the web worker work in profile/release mode?

nshahan commented 2 years ago

@jtmuller5 Thanks for the issue report. Based on what you described and a discussion with @sigmundch it sounds like one possibility is that dart2js is tree shaking away some type information in the presence of the web worker.

I see some code commented out, can you clarify that uncommenting these lines is required for the rerpo? https://github.com/jtmuller5/Flutter-Puzzle-Hack/blob/98ab3855678521d3c160eb7e536983dfa09193c6/lib/ui/home/home_view.dart#L207-L225

From your follow up message it sounds like the values being serialized in the message returned from the worker are not valid. I wanted to investigate it a little and I found that if I recompile the worker with a dart2js version: 2.17.0-150.0.dev it seems to work fine in release mode. It is possible this issue has already been fixed but I would like you to confirm? Could you try switching to the Flutter master channel and rebuild the worker with dart2js and then run your app?