Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP

Loading…

Allow building node as a library #3499

Open
wants to merge 1 commit into from

9 participants

@joelrbrandt

Node currently builds great as a shared or static library (for embedding in other applications).

However, the build scripts don't make this easy.

This change adds an optional --output-type command line option to configure to allow specifying a static or shared library build. It also fixes up vcbuild to allow setting output type on Windows.

configure
@@ -141,6 +141,11 @@ parser.add_option("--no-ifaddrs",
dest="no_ifaddrs",
help="Use on deprecated SunOS systems that do not support ifaddrs.h")
+parser.add_option("--output-type",
+ action="store",
+ dest="output_type",
+ help="Type of output binary to build. Valid values are: executable, static_library, shared_library (default: 'executable')")

Long line, wrap at 80 characters.

fixed, and also rebased to master

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
@bnoordhuis

The trouble with pull requests like this one is that pulling it in means supporting it. :-) Are there people besides you that will use this?

Other committers, what do you think?

@joelrbrandt

@bnoordhuis :-) I thought that was a very likely reaction.

I'm not personally aware of anyone else using it, but it seems like a really compelling use case for Node. People like to embed python/lua/ruby/etc. interpreters in apps. Node is right around the corner.

In case you're interested in my particular use case, I work on Brackets:
https://github.com/adobe/brackets
http://brackets.io

And, my work with Node is driven by this architectural endeavor:
https://github.com/adobe/brackets/wiki/Research:-Node.JS-Integration

@joelrbrandt

@bnoordhuis any further thoughts on this? Thanks again for your consideration.

@nathansobo

At GitHub we're also interested in embedding Node in an application. But in our case just building it as a library isn't enough. We need to figure out how to embed it without blocking our native application's event loop.

@joelrbrandt

@nathansobo Not to oversimplify things, but is there a reason you can't start Node (i.e. call node::Start) in its own thread?

I've got a simple mac test app that does this (with the dylib version of node) at https://github.com/joelrbrandt/node-shell/blob/master/src/mac/node-shell-lib/

This application starts node here: https://github.com/joelrbrandt/node-shell/blob/master/src/mac/node-shell-lib/node-shell-lib/AppDelegate.m#L31 (See also the NodeWrapper class).

And, it communicates with the UI thread using performSelectorOnMainThread like this: https://github.com/joelrbrandt/node-shell/blob/master/src/mac/node-shell-lib/node-shell-lib/CocoaWrapper.mm#L90

Hope that's helpful! Happy to chat further about this, but it probably makes sense to move the discussion to a different communication medium. :-) Feel free to shoot me an email.

@bnoordhuis

@joelrbrandt I'm going to let this stew a little more. I'm not dead set against the idea but until there's more demand, I don't want to merge it.

@joelrbrandt

@bnoordhuis No problem, thanks for letting me know.

Since we're using it, I'll be keeping the source branch of this pull updated/rebased to the latest v0.8.x release. If you decide you want to merge it, I'll be happy to fix it up for master. Just let me know.

@czaber

I would also be interested in embedding Node.js into my C application. It so much better than embedding pure V8, since there is a lot more libraries for Node.js.

@joelrbrandt are you still maintaining your fork of node.js with building as a shared library? I ask, because I missed anything like that in your repo.

@kilianc

+1

@joelrbrandt

@czaber @kilianc I just rebased the build-as-library branch in joelrbrandt/node to master. I also created the build-as-library-v0.8.4 branch in the same repo that builds the v0.8.4 release as a library.

To build, you need to do

./configure --output-type shared_library

Hope that helps!

@czaber

@joelrbrandt thanks! I had to add '-fPIC' flag to CXXFLAGS/CFLAGS in tools/gyp/pylib/gyp/generator/make.py and deps/npm/node_modules/node-gyp/legacy/tools/gyp/pylib/gyp/generator/make.py in order to build library on my Linux box.

@joelrbrandt

@czaber Thanks for the note -- exploring this on linux is on my backlog, but I haven't gotten to it yet.

I'm pretty surprised that gyp doesn't automatically set -fPIC for shared_library output types on linux. :-( Whenever I get around to working on linux support, I'll see if I can figure out how to set this by modifying node.gyp (or, less ideally, by modifying the configure script) rather than any of the tools files. If you figure it out, please send me a patch!

@bnoordhuis

-fPIC is not (or not always) required on some architectures and it can have a pretty severe impact on code speed and/or size, that's why.

@joelrbrandt

FYI: For anyone using this, I just rebased this source branch to (almost) master, as well as created the branch 'build-as-library-v0.8.8' which is based at the v0.8.8 tag. (All in the repo joelrbrandt/node )

@kilianc

I going to use it right now.

I think everyone who wants to embed node, is using it with NSTask ping/ponging and using stdin-stdout as some sort of IPC, it works but is so feeble and workaround-ish.

I think that supporting this would be a great value for the community.

@Nodejs-Jenkins

Can one of the admins verify this patch?

@hoonto

In my case I also had to split out node::Start into two separate functions, I needed the V8 context to be handed back to the wrapping application before dropping into uv_run. node::Start is like a main, a monolithic non-API entry point. So adding a couple API functions that allow the functionality in node::Start to be called, one stage at a time by a wrapping application would be handy. I happened to call the split up node::Start functions node::buildContext which builds the V8 context and node::runContext which then calls uv_run. However, the way I did it was pretty ugly I think there could be a much more clean way of doing it, hence not submitting a pull request for the work - but would love input on how I could achieve this better, etc. I'd be happy to do the work on cleaning it up and submitting pull request. Oh, the branch I reference is: https://github.com/hoonto/plnode (v0.10.12-plnode-0.0.1) where changes are in node.cc and node.h. I posted to node.js google group but no response there, probably I was in the wrong place. Also that was on the 0.10 stable, node::Start has changed in master, so of course this plnode piece doesn't work on the latest master, but easy to update would just need the isolate stuff.

@Mithgol

I posted to node.js google group but no response there, probably I was in the wrong place.

The correct Google Group is not “node.js” but “nodejs” (without the dot). So you was in the wrong place (unless you've visited the nodejs group but later here added the dot).

@hoonto

@Mithgol Yes, thank you for the correction, you are right I added the dot here later - I was in nodejs

@ellisium

hi everybody,

I build node.js as a shared_library and my main program compile.
However when I call node::Start I hit this exception:

        char* argv[] = {(char *) "node",  (char *) "/home/test.js" };   
    int argc = 2;
    node::Start(argc, argv);

../deps/uv/src/unix/proctitle.c:54: uv_setup_args: Assertion `process_title.len + 1 == size' failed.

argc and argv seems right, so I've no idea about this problem.

Node version is : v0.10.13 under ubuntu 12.04 LTS

Someone have succesfull with a recent node.js build as shared_library?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Commits on Sep 1, 2012
  1. @joelrbrandt
This page is out of date. Refresh to see the latest.
Showing with 14 additions and 3 deletions.
  1. +7 −0 configure
  2. +1 −1  node.gyp
  3. +6 −2 vcbuild.bat
View
7 configure
@@ -165,6 +165,12 @@ parser.add_option("--with-arm-float-abi",
help="Specifies which floating-point ABI to use. Valid values are: "
"soft, softfp, hard")
+parser.add_option("--output-type",
+ action="store",
+ dest="output_type",
+ help="""Type of output binary to build. Valid values are:
+ executable, static_library, shared_library (default: 'executable')""")
+
(options, args) = parser.parse_args()
@@ -317,6 +323,7 @@ def configure_node(o):
o['variables']['node_prefix'] = os.path.expanduser(options.prefix or '')
o['variables']['node_install_npm'] = b(not options.without_npm)
o['default_configuration'] = 'Debug' if options.debug else 'Release'
+ o['variables']['output_type'] = options.output_type or 'executable'
host_arch = host_arch_win() if os.name == 'nt' else host_arch_cc()
target_arch = options.dest_cpu or host_arch
View
2  node.gyp
@@ -54,7 +54,7 @@
'targets': [
{
'target_name': 'node',
- 'type': 'executable',
+ 'type': '<(output_type)',
'dependencies': [
'deps/cares/cares.gyp:cares',
View
8 vcbuild.bat
@@ -16,6 +16,7 @@ set config=Release
set msiplatform=x86
set target=Build
set target_arch=ia32
+set output_type=executable
set debug_arg=
set nosnapshot_arg=
set noprojgen=
@@ -41,6 +42,8 @@ if /i "%1"=="clean" set target=Clean&goto arg-ok
if /i "%1"=="ia32" set target_arch=ia32&goto arg-ok
if /i "%1"=="x86" set target_arch=ia32&goto arg-ok
if /i "%1"=="x64" set target_arch=x64&goto arg-ok
+if /i "%1"=="sharedlibrary" set output_type=shared_library&goto arg-ok
+if /i "%1"=="staticlibrary" set output_type=static_library&goto arg-ok
if /i "%1"=="noprojgen" set noprojgen=1&goto arg-ok
if /i "%1"=="nobuild" set nobuild=1&goto arg-ok
if /i "%1"=="nosign" set nosign=1&goto arg-ok
@@ -80,7 +83,7 @@ if defined noetw set noetw_arg=--without-etw& set noetw_msi_arg=/p:NoETW=1
if defined noprojgen goto msbuild
@rem Generate the VS project.
-python configure %debug_arg% %nosnapshot_arg% %noetw_arg% --dest-cpu=%target_arch%
+python configure %debug_arg% %nosnapshot_arg% %noetw_arg% --dest-cpu=%target_arch% --output-type=%output_type%
if errorlevel 1 goto create-msvs-files-failed
if not exist node.sln goto create-msvs-files-failed
echo Project files generated.
@@ -187,12 +190,13 @@ python tools/closure_linter/closure_linter/gjslint.py --unix_mode --strict --noj
goto exit
:help
-echo vcbuild.bat [debug/release] [msi] [test-all/test-uv/test-internet/test-pummel/test-simple/test-message] [clean] [noprojgen] [nobuild] [nosign] [x86/x64]
+echo vcbuild.bat [debug/release] [msi] [test-all/test-uv/test-internet/test-pummel/test-simple/test-message] [clean] [noprojgen] [nobuild] [nosign] [x86/x64] [sharedlibrary/staticlibrary]
echo Examples:
echo vcbuild.bat : builds release build
echo vcbuild.bat debug : builds debug build
echo vcbuild.bat release msi : builds release build and MSI installer package
echo vcbuild.bat test : builds debug build and runs tests
+echo vcbuild.bat sharedlibrary : builds release build as a dll
goto exit
:exit
Something went wrong with that request. Please try again.