Skip to content
This repository has been archived by the owner on Feb 12, 2024. It is now read-only.

Runtime Support: Electron & Muon #843

Closed
daviddias opened this issue May 7, 2017 · 18 comments
Closed

Runtime Support: Electron & Muon #843

daviddias opened this issue May 7, 2017 · 18 comments
Assignees
Labels
exp/wizard Extensive knowledge (implications, ramifications) required help wanted Seeking public contribution on this issue P0 Critical: Tackled by core team ASAP

Comments

@daviddias
Copy link
Member

daviddias commented May 7, 2017

More and more user's have been having trouble using js-ipfs with Electron due to the native module dependencies, see:

The solution found passes by following this example: https://github.com/electron/electron/blob/master/docs/tutorial/using-native-node-modules.md

We should include instructions to guide users to follow that and also run tests in Electron's Node.js Process + Browser process just to be sure #697

Update: I've started tackling this issue, follow the rest of the thread to check the state of things. tl;dr; You should be able to run js-ipfs in the browser process of Electron just fine if you webpack/browserify js-ipfs, running in the main process (aka Node.js) is stil a ❓ due to native dependencies.

@daviddias daviddias added exp/novice Someone with a little familiarity can pick up help wanted Seeking public contribution on this issue labels May 7, 2017
@daviddias daviddias added exp/expert Having worked on the specific codebase is important and removed exp/novice Someone with a little familiarity can pick up labels Jun 27, 2017
@daviddias daviddias changed the title Need better instructions for Electron users. Review Electron main process support - Need better instructions for Electron users. Jun 27, 2017
@daviddias
Copy link
Member Author

I believe that the short term solution is making libp2p recipe's pluggable on node boot so that libp2p-webrtc-star can be added if the user wants. Then I can break libp2p-webrtc-star into libp2p-webrtc-star-browser and libp2p-webrtc-star-nodejs, having the nodejs one installed a posteriori by the users if the user wants.

@daviddias
Copy link
Member Author

daviddias commented Jun 28, 2017

What would others say it is the best approach here:

  • a) Have two versions of webrtc-star published: -nodejs and -browser
  • b) Support for DI of the wrtc module.

Initially, I was more thinking of a), but to avoid code duplication and double publishing to npm, I'm not more inclined to b).

The end result is the same if you are running js-ipfs in Node.js, it doesn't bring webrtc-star out of the box, however, if you:

const IPFS = require('ipfs')
const wrtc = require('wrtc')
const WStar = require('libp2p-webrtc-star'))

const node = new IPFS({
  libp2p: {
    modules: {
      transports: [
         new WStar(wrtc)
      ]
    }
  }
})

You get WebRTC in Node.js again.

This would take out all of the compilation issues with electron and enable users to use IPFS with the other transports.

@pgte
Copy link
Contributor

pgte commented Jun 28, 2017

except for wrtc, libp2p-webrtc-star doesn't seam to have any logic specific to any environment, so I suggest using DI, with detailed instructions specific for electron on js-ipfs..

@daviddias daviddias changed the title Review Electron main process support - Need better instructions for Electron users. The road for Electron support! Jun 29, 2017
@daviddias
Copy link
Member Author

daviddias commented Jun 29, 2017

Ok, the first 🐉, wrtc, is slayed with #884.

I'm still seeing issues with other native dependencies. #884 adds an electron example so that it is quick to test. Any experienced electron devs out there that could check it as well?

@kenshyx, @josselinchevalay, @kyledrake, @negamaxi et all :)

@daviddias daviddias added exp/wizard Extensive knowledge (implications, ramifications) required and removed exp/expert Having worked on the specific codebase is important labels Jun 29, 2017
@kenshyx
Copy link
Contributor

kenshyx commented Jun 29, 2017

Hello, I just tested it in renderer process. Unfortunately it doesn't work because I need to install it with --no-optional and it breaks the node-webcrypto-ossl dependency which doesnt work on electron.
Module not found: Error: Can't resolve 'node-webcrypto-ossl' in 'node_modules/libp2p-crypto/src/crypto'

webpack: v3.0.0

@daviddias
Copy link
Member Author

Are you using latest js-ipfs master? node-webcrypto-ossl is just used in Node.js, in the Browser it uses WebCrypto directly. Investigating..

@kenshyx
Copy link
Contributor

kenshyx commented Jun 30, 2017

Yes, I used latest js-ipfs from master. I forgot to specify that error Module not found: Error: Can't resolve 'node-webcrypto-ossl' in 'node_modules/libp2p-crypto/src/crypto' comes from webpack.

@negamaxi
Copy link
Contributor

negamaxi commented Jul 7, 2017

Hi there. Just cloned this repo, main npm install ends well, npm install in examples/electron ends with an error on electron-rebuild stage (some localized text inside):


> [email protected] postinstall /mnt/sda5/Projects/js-ipfs/examples/electron
> electron-rebuild

✖ Rebuild Failed
An unhandled error occurred inside electron-rebuild
make: вход в каталог «/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/execSync/build»
  CXX(target) Release/obj.target/shell/src/shell.o
../src/shell.cpp:138:26: ошибка: «Arguments» не является именем типа
 Handle<Value> Exec(const Arguments& args) {
                          ^~~~~~~~~
../src/shell.cpp: В функции «v8::Handle<v8::Value> Exec(const int&)»:
../src/shell.cpp:139:17: ошибка: «v8::HandleScope::HandleScope()» is protected within this context
     HandleScope scope;
                 ^~~~~
In file included from /home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/src/node.h:42:0,
                 from ../src/shell.cpp:1:
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:874:13: замечание: declared protected here
   V8_INLINE HandleScope() {}
             ^~~~~~~~~~~
../src/shell.cpp:141:14: ошибка: запрос элемента «Length» в «args», имеющего не классовый тип «const int»
     if (args.Length() < 1) {
              ^~~~~~
../src/shell.cpp:143:34: ошибка: «New» не является элементом «v8::String»
             Exception::TypeError(String::New("First argument must be a string"))
                                  ^~~~~~
../src/shell.cpp:144:9: ошибка: нет декларации «ThrowException» в этой области видимости
         );
         ^
../src/shell.cpp:147:31: ошибка: некорректные типы «const int[int]» для индекса массива
     Local<String> str = args[0]->ToString();
                               ^
../src/shell.cpp:151:18: ошибка: «class v8::HandleScope» has no member named «Close»
     return scope.Close(Integer::New(result));
                  ^~~~~
../src/shell.cpp:151:43: ошибка: нет подходящей функции для вызова «v8::Integer::New(int&)»
     return scope.Close(Integer::New(result));
                                           ^
In file included from /home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/src/node.h:42:0,
                 from ../src/shell.cpp:1:
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:2756:25: замечание: candidate: static v8::Local<v8::Integer> v8::Integer::New(v8::Isolate*, int32_t)
   static Local<Integer> New(Isolate* isolate, int32_t value);
                         ^~~
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:2756:25: замечание:   кандидат ожидает 2 аргумента, 1 предоставлено
../src/shell.cpp: В функции «void RegisterModule(v8::Handle<v8::Object>)»:
../src/shell.cpp:155:17: ошибка: «NewSymbol» не является элементом «v8::String»
     target->Set(String::NewSymbol("exec"),
                 ^~~~~~
../src/shell.cpp:156:39: ошибка: нет подходящей функции для вызова «v8::FunctionTemplate::New(v8::Handle<v8::Value> (&)(const int&))»
             FunctionTemplate::New(Exec)->GetFunction());
                                       ^
In file included from /home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/src/node.h:42:0,
                 from ../src/shell.cpp:1:
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:5090:34: замечание: candidate: static v8::Local<v8::FunctionTemplate> v8::FunctionTemplate::New(v8::Isolate*, v8::FunctionCallback, v8::Local<v8::Value>, v8::Local<v8::Signature>, int, v8::ConstructorBehavior)
   static Local<FunctionTemplate> New(
                                  ^~~
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:5090:34: замечание:   нет известных преобразований для аргумента 1 из «v8::Handle<v8::Value>(const int&) {aka v8::Local<v8::Value>(const int&)}» в «v8::Isolate*»
shell.target.mk:92: ошибка выполнения рецепта для цели «Release/obj.target/shell/src/shell.o»
make: выход из каталога «/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/execSync/build»
make: *** [Release/obj.target/shell/src/shell.o] Ошибка 1
gyp ERR! build error 
gyp ERR! stack Error: `make` failed with exit code: 2
gyp ERR! stack     at ChildProcess.onExit (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/node-gyp/lib/build.js:258:23)
gyp ERR! stack     at emitTwo (events.js:106:13)
gyp ERR! stack     at ChildProcess.emit (events.js:194:7)
gyp ERR! stack     at Process.ChildProcess._handle.onexit (internal/child_process.js:215:12)
gyp ERR! System Linux 4.11.8-200.fc25.x86_64
gyp ERR! command "/usr/bin/node" "/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/.bin/node-gyp" "rebuild" "--target=1.6.11" "--arch=x64" "--dist-url=https://atom.io/download/electron" "--build-from-source"
gyp ERR! cwd /mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/execSync
gyp ERR! node -v v7.10.0
gyp ERR! node-gyp -v v3.6.2
gyp ERR! not ok 

Failed with exit code: 1

Error: make: вход в каталог «/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/execSync/build»
  CXX(target) Release/obj.target/shell/src/shell.o
../src/shell.cpp:138:26: ошибка: «Arguments» не является именем типа
 Handle<Value> Exec(const Arguments& args) {
                          ^~~~~~~~~
../src/shell.cpp: В функции «v8::Handle<v8::Value> Exec(const int&)»:
../src/shell.cpp:139:17: ошибка: «v8::HandleScope::HandleScope()» is protected within this context
     HandleScope scope;
                 ^~~~~
In file included from /home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/src/node.h:42:0,
                 from ../src/shell.cpp:1:
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:874:13: замечание: declared protected here
   V8_INLINE HandleScope() {}
             ^~~~~~~~~~~
../src/shell.cpp:141:14: ошибка: запрос элемента «Length» в «args», имеющего не классовый тип «const int»
     if (args.Length() < 1) {
              ^~~~~~
../src/shell.cpp:143:34: ошибка: «New» не является элементом «v8::String»
             Exception::TypeError(String::New("First argument must be a string"))
                                  ^~~~~~
../src/shell.cpp:144:9: ошибка: нет декларации «ThrowException» в этой области видимости
         );
         ^
../src/shell.cpp:147:31: ошибка: некорректные типы «const int[int]» для индекса массива
     Local<String> str = args[0]->ToString();
                               ^
../src/shell.cpp:151:18: ошибка: «class v8::HandleScope» has no member named «Close»
     return scope.Close(Integer::New(result));
                  ^~~~~
../src/shell.cpp:151:43: ошибка: нет подходящей функции для вызова «v8::Integer::New(int&)»
     return scope.Close(Integer::New(result));
                                           ^
In file included from /home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/src/node.h:42:0,
                 from ../src/shell.cpp:1:
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:2756:25: замечание: candidate: static v8::Local<v8::Integer> v8::Integer::New(v8::Isolate*, int32_t)
   static Local<Integer> New(Isolate* isolate, int32_t value);
                         ^~~
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:2756:25: замечание:   кандидат ожидает 2 аргумента, 1 предоставлено
../src/shell.cpp: В функции «void RegisterModule(v8::Handle<v8::Object>)»:
../src/shell.cpp:155:17: ошибка: «NewSymbol» не является элементом «v8::String»
     target->Set(String::NewSymbol("exec"),
                 ^~~~~~
../src/shell.cpp:156:39: ошибка: нет подходящей функции для вызова «v8::FunctionTemplate::New(v8::Handle<v8::Value> (&)(const int&))»
             FunctionTemplate::New(Exec)->GetFunction());
                                       ^
In file included from /home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/src/node.h:42:0,
                 from ../src/shell.cpp:1:
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:5090:34: замечание: candidate: static v8::Local<v8::FunctionTemplate> v8::FunctionTemplate::New(v8::Isolate*, v8::FunctionCallback, v8::Local<v8::Value>, v8::Local<v8::Signature>, int, v8::ConstructorBehavior)
   static Local<FunctionTemplate> New(
                                  ^~~
/home/negamaxi/.electron-gyp/.node-gyp/iojs-1.6.11/deps/v8/include/v8.h:5090:34: замечание:   нет известных преобразований для аргумента 1 из «v8::Handle<v8::Value>(const int&) {aka v8::Local<v8::Value>(const int&)}» в «v8::Isolate*»
shell.target.mk:92: ошибка выполнения рецепта для цели «Release/obj.target/shell/src/shell.o»
make: выход из каталога «/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/execSync/build»
make: *** [Release/obj.target/shell/src/shell.o] Ошибка 1
gyp ERR! build error 
gyp ERR! stack Error: `make` failed with exit code: 2
gyp ERR! stack     at ChildProcess.onExit (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/node-gyp/lib/build.js:258:23)
gyp ERR! stack     at emitTwo (events.js:106:13)
gyp ERR! stack     at ChildProcess.emit (events.js:194:7)
gyp ERR! stack     at Process.ChildProcess._handle.onexit (internal/child_process.js:215:12)
gyp ERR! System Linux 4.11.8-200.fc25.x86_64
gyp ERR! command "/usr/bin/node" "/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/.bin/node-gyp" "rebuild" "--target=1.6.11" "--arch=x64" "--dist-url=https://atom.io/download/electron" "--build-from-source"
gyp ERR! cwd /mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/execSync
gyp ERR! node -v v7.10.0
gyp ERR! node-gyp -v v3.6.2
gyp ERR! not ok 

Failed with exit code: 1
    at SafeSubscriber._error (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/spawn-rx/lib/src/index.js:267:84)
    at SafeSubscriber.__tryOrUnsub (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/rxjs/Subscriber.js:238:16)
    at SafeSubscriber.error (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/rxjs/Subscriber.js:197:26)
    at Subscriber._error (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/rxjs/Subscriber.js:128:26)
    at Subscriber.error (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/rxjs/Subscriber.js:102:18)
    at MapSubscriber.Subscriber._error (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/rxjs/Subscriber.js:128:26)
    at MapSubscriber.Subscriber.error (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/rxjs/Subscriber.js:102:18)
    at SafeSubscriber._next (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/spawn-rx/lib/src/index.js:241:65)
    at SafeSubscriber.__tryOrSetError (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/rxjs/Subscriber.js:247:16)
    at SafeSubscriber.next (/mnt/sda5/Projects/js-ipfs/examples/electron/node_modules/rxjs/Subscriber.js:187:27)

npm WARN optional SKIPPING OPTIONAL DEPENDENCY: fsevents@^1.0.0 (node_modules/chokidar/node_modules/fsevents):
npm WARN notsup SKIPPING OPTIONAL DEPENDENCY: Unsupported platform for [email protected]: wanted {"os":"darwin","arch":"any"} (current: {"os":"linux","arch":"x64"})
npm WARN [email protected] No repository field.
npm ERR! Linux 4.11.8-200.fc25.x86_64
npm ERR! argv "/usr/bin/node" "/usr/bin/npm" "install"
npm ERR! node v7.10.0
npm ERR! npm  v4.2.0
npm ERR! code ELIFECYCLE
npm ERR! errno 255
npm ERR! [email protected] postinstall: `electron-rebuild`
npm ERR! Exit status 255
npm ERR! 
npm ERR! Failed at the [email protected] postinstall script 'electron-rebuild'.
npm ERR! Make sure you have the latest version of node.js and npm installed.
npm ERR! If you do, this is most likely a problem with the js-ipfs-in-electron package,
npm ERR! not with npm itself.
npm ERR! Tell the author that this fails on your system:
npm ERR!     electron-rebuild
npm ERR! You can get information on how to open an issue for this project with:
npm ERR!     npm bugs js-ipfs-in-electron
npm ERR! Or if that isn't available, you can get their info via:
npm ERR!     npm owner ls js-ipfs-in-electron
npm ERR! There is likely additional logging output above.

npm ERR! Please include the following file with any support request:
npm ERR!     /home/negamaxi/.npm/_logs/2017-07-07T17_46_54_901Z-debug.log

@daviddias daviddias added the status/ready Ready to be worked label Jul 9, 2017
@daviddias
Copy link
Member Author

Just finished migrating off one of the offenders to make this happen (node-webcrypto-ossl). Now, the new one is: uws:

An unhandled error occurred inside electron-rebuild
  CXX(target) Release/obj.target/uws/src/Extensions.o
  CXX(target) Release/obj.target/uws/src/Group.o
In file included from ../src/Group.cpp:1:
In file included from ../src/Group.h:4:
In file included from ../src/WebSocket.h:4:
In file included from ../src/WebSocketProtocol.h:5:
../src/Networking.h:7:10: fatal error: 'openssl/opensslv.h' file not found
#include <openssl/opensslv.h>

this one comes from libp2p-webrtc-star use of socket.io. We can move away from socket.io

@dryajov
Copy link
Member

dryajov commented Sep 21, 2017

Is this still an issue? I've haven't been able to reproduce any of the issues linked here. I've so far been successful in running IPFS in the main and renderer processes.

I'll be concentrating on - ipfs/aegir#157.

@negamaxi
Copy link
Contributor

negamaxi commented Sep 23, 2017

  1. Still experiencing Uncaught TypeError: createServer is not a function using 0.26.0 IPFS bundle from cdn via script tag and trying to start ipfs node in a renderer.js.

  2. Using 0.26.0 npm module in the renderer.js I get an error with following message in devTools:
    "Failed to require LevelDOWN (The module '/mnt/sda5/Projects/electron-ipfs-quick-start/node_modules/leveldown/build/Release/leveldown.node'↵was compiled against a different Node.js version using↵NODE_MODULE_VERSION 51. This version of Node.js requires↵NODE_MODULE_VERSION 54. Please try re-compiling or re-installing↵the module (for instance, using `npm rebuild` or`npm install`).). Try `npm install leveldown` if it's missing".
    2.1 doing npm rebuild or npm install or npm install leveldown didn't help.
    2.2 same error popups in a modal window trying to use ipfs in a main.js.

Node.js 7.9.0, Chromium 58.0.3029.110, and Electron 1.7.6.

@dryajov
Copy link
Member

dryajov commented Sep 25, 2017

@negamaxi I was able to reproduce the error with electron version - 1.7.6.

The issues is not specifically related to the version of electron, but the version that the native modules are built with - electron 1.7.6 is using a different node version (7.9.0 in this case) that the one the modules are being installed with - electron-rebuild should help with that however it is breaking for me when I try running it. I'll continue to troubleshoot this issue.

@dryajov
Copy link
Member

dryajov commented Sep 26, 2017

@negamaxi

Building with npm by executing the bellow script works for me:

# Electron's version.
export npm_config_target=1.7.6
# The architecture of Electron, can be ia32 or x64.
export npm_config_arch=x64
export npm_config_target_arch=x64
# Download headers for Electron.
export npm_config_disturl=https://atom.io/download/electron
# Tell node-pre-gyp that we are building for Electron.
export npm_config_runtime=electron
# Tell node-pre-gyp to build module from source code.
export npm_config_build_from_source=true
# Install all dependencies, and store cache to ~/.electron-gyp.
HOME=~/.electron-gyp npm install

Could you try it out and let me know if it works for you as well?

Building with electron-rebuild is still an issue.

@negamaxi
Copy link
Contributor

@dryajov confirmed, it works.

@daviddias daviddias added P0 Critical: Tackled by core team ASAP status/ready Ready to be worked and removed status/ready Ready to be worked labels Oct 17, 2017
daviddias added a commit that referenced this issue Dec 20, 2017
daviddias added a commit that referenced this issue Dec 28, 2017
* docs: add FAQ about Electron

ref: #843 (comment)

* Update README.md

* Update README.md
@linonetwo
Copy link

linonetwo commented Feb 2, 2018

You could use a postinstall script like:

"postinstall":
      "cd ./src && cross-env npm_config_target=1.7.12 npm_config_arch=x64 npm_config_target_arch=x64 npm_config_disturl=https://atom.io/download/electron npm_config_runtime=electron npm_config_build_from_source=true HOME=~/.electron-gyp yarn"

copy from @dryajov 's example and change the electron version.

@pvh
Copy link

pvh commented Feb 16, 2018

I was building an Electron / IPFS app and it had a devil of a time with Windows builds because of UWS. The UWS author appears disinclined to support Electron, and but it can be made to work by fixing how the binding.gyp links SSL libraries. Simply put you need to add 'libraries': ['libeay32', 'ssleay32'] to the stanza in there which refers to os == 'win'. I haven't got the energy to pursue this with the upstream author but if you or anyone else wants to get it working, that's how.

The previous problem noted above (missing opensslv.h) is solved by following the directions on the UWS repo: install vcpkg, and then install the UWS dependencies he lists there.

@linonetwo
Copy link

If you are using ipfsd-ctl to start an ipfs instance and run into trouble like NODE_MODULE_VERSION 57 NODE_MODULE_VERSION 59 xxx, you can try

const DaemonFactory = require('ipfsd-ctl');
const ipfsDaemon = DaemonFactory.create({ type: 'proc', exec: require('ipfs') });

Instead of DaemonFactory.create({ type: 'js' });

Since we have built native modules to match nodejs version inside the electron, and ipfsd-ctl will try to run your built module on the nodejs outside the electron (the one on your working environment).

@daviddias daviddias changed the title Electron support Runtime Support: Electron & Muon Mar 16, 2018
@daviddias daviddias mentioned this issue Apr 3, 2018
@daviddias
Copy link
Member Author

There is now full support with the last dragon slayed by @leo6104! \o/

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
exp/wizard Extensive knowledge (implications, ramifications) required help wanted Seeking public contribution on this issue P0 Critical: Tackled by core team ASAP
Projects
None yet
Development

No branches or pull requests

7 participants