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

How to use with webdev #72

Open
Timmmm opened this issue Nov 18, 2019 · 1 comment
Open

How to use with webdev #72

Timmmm opened this issue Nov 18, 2019 · 1 comment

Comments

@Timmmm
Copy link

Timmmm commented Nov 18, 2019

This is more of a question than an issue: How do I use this with webdev?

Until now I had build_web_compilers in my pubspec.yaml, a web/index.html file, web/main.dart, and an index.js file to run Electron and have it show localhost:8080.

That worked great, until I tried to use node_interop. My code compiles but I get a runtime error about the module not being loaded. I presumed that is because I need to use build_node_compilers instead of build_web_compilers.

I swapped that in pubspec.yaml, and renamed the web directory to node, but when I run webdev serve node:8080 it gives error:

webdev could not run for this project.
You must have a dependency on `build_web_compilers` in `pubspec.yaml`.

If I add them both then I get this error:

Ok well I was getting an error like Could not find web/index.html or index.html, but now I get this, even after removing .dart_tool:

[SEVERE] The platform `ddc`, has already been registered.

[SEVERE] Failed to instantiate builder for collection with configuration:
{}
Unhandled exception:
Bad state: Unable to start build daemon.
#0      _handleDaemonStartup (package:build_daemon/client.dart:82:5)
<asynchronous suspension>
#1      BuildDaemonClient.connect (package:build_daemon/client.dart:183:11)
<asynchronous suspension>
#2      connectClient (package:webdev/src/daemon_client.dart:17:23)
#3      _startBuildDaemon (package:webdev/src/serve/dev_workflow.dart:25:18)
<asynchronous suspension>
#4      DevWorkflow.start (package:webdev/src/serve/dev_workflow.dart:173:24)
<asynchronous suspension>
#5      ServeCommand.run (package:webdev/src/command/serve_command.dart:138:27)
<asynchronous suspension>
#6      CommandRunner.runCommand (package:args/command_runner.dart:197:27)
<asynchronous suspension>
#7      _CommandRunner.runCommand (package:webdev/src/webdev_command_runner.dart:38:24)
<asynchronous suspension>
#8      CommandRunner.run.<anonymous closure> (package:args/command_runner.dart:112:25)
#9      new Future.sync (dart:async/future.dart:222:31)
#10     CommandRunner.run (package:args/command_runner.dart:112:14)
#11     run (package:webdev/src/webdev_command_runner.dart:19:56)
#12     main (file:///Users/timh/.pub-cache/hosted/pub.dartlang.org/webdev-2.5.1/bin/webdev.dart:17:22)
<asynchronous suspension>
#13     _startIsolate.<anonymous closure> (dart:isolate-patch/isolate_patch.dart:303:32)
#14     _RawReceivePortImpl._handleMessage (dart:isolate-patch/isolate_patch.dart:172:12)

How is this supposed to work?

@Timmmm
Copy link
Author

Timmmm commented Nov 19, 2019

Aha I figured it out! For any people trying to get Electron to work... the problem is as follows.

First, I enabled nodeIntegration in my Electron entry point:

  win = new BrowserWindow({
    width: 800,
    height: 600,
    webPreferences: {
      // Allow using node APIs from the web context.
      nodeIntegration: true,
    },

This means that Electron adds the Node APIs to the web page when the page is loaded in an Electron window. This means you can do stuff like loading files, running processes etc. from your web page (running in Electron) that you couldn't do.

However if you simply webdev serve and then do

  win.loadURL("http://localhost:8080");

in your index.js, you will find a problem. Electron adds window.require() which is Node's special require() function. The problem is that webdev, or maybe some part of AngularDart, also uses a require() function, but a different one! So you'll get some error about require().

This is mentioned in the Electron docs and I copied their solution:

<script>
window.nodeRequire = require;
delete window.require;
delete window.exports;
delete window.module;
</script>

And everything worked... until I tried to use node_interop. The problem is that node_interop calls require() and it expects it to be Node's require(). Since it is actually calling AngularDart's require() you get a very confusing and incorrect error message.

I have now "solved" this by changing this code in node.dart:

external dynamic require(String id);

To this:

external dynamic nodeRequire(String id);
dynamic require(String id) {
  return nodeRequire(id);
}

It would be great if there were an option to do this somehow.

Also, my attempt to use build_node_compilers was a red herring - my code isn't actually running in the main Node process, so it doesn't need to be compiled as Node modules. ES6 modules (or whatever webdev uses) work fine.

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

1 participant