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

NPM dependencies #111

Closed
marceln opened this issue May 26, 2021 · 2 comments
Closed

NPM dependencies #111

marceln opened this issue May 26, 2021 · 2 comments

Comments

@marceln
Copy link

marceln commented May 26, 2021

Hi,

Couldn't find any documentation (or maybe I missed it) on how to use it when using npm dependencies in the module you're executing. Found a few entries here, in the issues, but I'd like to know things like: does it use a packages.json, if present on disk and who runs npm install?

Also, nice lib btw.

Thanks

@JeremyTCD
Copy link
Member

JeremyTCD commented May 26, 2021

Yeah our docs don't cover it, could be improved. I've created an example project to clarify things: Example.UsingNpmModules. To use the example

  • Clone it
  • Run npm install in the Javascript folder
  • Run the project in visual studio (ctrl f5)

In general, for you own projects, you'll want to create a folder in your project for your package.json and call npm install manually. Then you'll want to configure MSBuild to copy the folder to your output directory on build.

In the example I named the folder Javascript, and configured MSBuild to copy it by adding the following to the .csproj:

<ItemGroup>
    <None Include="./Javascript/**" CopyToOutputDirectory="PreserveNewest" />
</ItemGroup>

In your logic you'll have to set NodeJSProcessOptions.ProjectPath to the folder in your output directory. Once all that's done you can require your npm modules.

For quick reference, here's the example project's Main:

static async Task Main()
{
    // Create INodeJSService
    var serviceCollection = new ServiceCollection();
    serviceCollection.AddNodeJS();
    serviceCollection.Configure<NodeJSProcessOptions>(options => options.ProjectPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Javascript")); // AppDomain.CurrentDomain.BaseDirectory is your bin/<configuration>/<targetframework> directory
    var serviceProvider = serviceCollection.BuildServiceProvider();
    var nodeJSService = serviceProvider.GetRequiredService<INodeJSService>();

    // Invoke from file
    string result1 = await nodeJSService.InvokeFromFileAsync<string>("./interop.js", args: new[] { "testString" }).ConfigureAwait(false);
    Console.WriteLine(result1);

    // Invoke from string
    string interopModuleString = @"const lodash = require('lodash');

module.exports = (callback, arg) => {
callback(null, lodash.snakeCase(arg));
}";
    string result2 = await nodeJSService.InvokeFromStringAsync<string>(interopModuleString, args: new[] { "testString" }).ConfigureAwait(false);
    Console.WriteLine(result2);

    // Expected output:
    //
    // test-string
    // test_string
}

interop.js:

const lodash = require('lodash');

module.exports = (callback, arg) => {
    callback(null, lodash.kebabCase(arg));
}

Once you get all that working, you can consider automating package restoration. You might also want to bundle your js. You can do both those things with Yarn.MSBuild. It's a bit involved, if you're interested let me know I'll add it to the example.

@marceln
Copy link
Author

marceln commented May 26, 2021

Thanks man, I think that's enough to get me going. Appreciate it.
Also, this looks comprehensive enough to put in readme.md.

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

2 participants