Skip to content

Feature/start process with custom arguments #9

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

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,7 @@ import nodejs from 'nodejs-mobile-react-native';
```

- `nodejs.start`
- `nodejs.startWithArgs`
- `nodejs.startWithScript`
- `nodejs.channel.addListener`
- `nodejs.channel.post`
Expand All @@ -138,6 +139,15 @@ import nodejs from 'nodejs-mobile-react-native';

Starts the nodejs-mobile runtime thread with a file inside the `nodejs-project` directory.

### nodejs.startWithArgs(command [, options])

| Param | Type |
| --- | --- |
| command | <code>string</code> |
| options | <code>[StartupOptions](#ReactNative.StartupOptions)</code> |

Starts the nodejs-mobile runtime thread with a file inside the `nodejs-project` directory and passes provided arguments down to it.

### nodejs.startWithScript(scriptBody [, options])

| Param | Type |
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -189,6 +189,43 @@ public void run() {
}
}

@ReactMethod
public void startNodeProjectWithArgs(final String input, ReadableMap options) throws Exception {
// A New module instance may have been created due to hot reload.
_instance = this;
if(!_startedNodeAlready) {
_startedNodeAlready = true;

List<String> args = new ArrayList<String>(Arrays.asList(input.split(" ")));

String absoluteScriptPath = nodeJsProjectPath + "/" + args.get(0);

// Remove script file name from arguments list
args.remove(0);

final List<String> command = new ArrayList<String>();

command.add("node");
command.add(absoluteScriptPath);

command.addAll(args);

final boolean redirectOutputToLogcat = extractRedirectOutputToLogcatOption(options);

new Thread(new Runnable() {
@Override
public void run() {
waitForInit();
startNodeWithArguments(
command.toArray(new String[0]),
nodeJsProjectPath + ":" + builtinModulesPath,
redirectOutputToLogcat
);
}
}).start();
}
}

@ReactMethod
public void sendMessage(String channel, String msg) {
sendMessageToNodeChannel(channel, msg);
Expand Down
6 changes: 6 additions & 0 deletions index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,12 @@ declare module "nodejs-mobile-react-native" {
* @param options
*/
start: (scriptFileName: string, options?: StartupOptions) => void
/**
* Starts the nodejs-mobile runtime thread with provided arguments
* @param command
* @param options
*/
startWithArgs: (command: string, options?: StartupOptions) => void
/**
* Starts the nodejs-mobile runtime thread with a script body
* @param scriptBody
Expand Down
10 changes: 10 additions & 0 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,15 @@ const start=function(mainFileName, options) {
options = options || {};
RNNodeJsMobile.startNodeProject(mainFileName, options);
};

const startWithArgs=function(command, options) {
if (typeof command !== 'string') {
throw new Error('nodejs-mobile-react-native\'s startWithArgs expects to receive the main .js entrypoint filename with optional arguments, e.g.: nodejs.startWithArgs("main.js -c custom");');
}
options = options || {};
RNNodeJsMobile.startNodeProjectWithArgs(command, options);
};

const startWithScript=function(script, options) {
options = options || {};
RNNodeJsMobile.startNodeWithScript(script, options);
Expand Down Expand Up @@ -117,6 +126,7 @@ registerChannel(eventChannel);

const export_object = {
start: start,
startWithArgs: startWithArgs,
startWithScript: startWithScript,
channel: eventChannel
};
Expand Down
53 changes: 53 additions & 0 deletions ios/RNNodeJsMobile.m
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,42 @@ -(void)callStartNodeProject:(NSString *)mainFileName
[[NodeRunner sharedInstance] startEngineWithArguments:nodeArguments:nodePath];
}

-(void)callStartNodeProjectWithArgs:(NSString *)input
{
NSArray* command = [input componentsSeparatedByString: @" "];
NSString* script = [command objectAtIndex:0];

NSMutableArray* args = [command mutableCopy];
[args removeObject:[args objectAtIndex:0]];

NSString* srcPath = [[NSBundle mainBundle] pathForResource:[NSString stringWithFormat:@"%@/%@", NODEJS_PROJECT_RESOURCE_PATH, script] ofType:@""];

NSMutableArray* nodeArguments = nil;

NSString* dlopenoverridePath = [[NSBundle mainBundle] pathForResource:[NSString stringWithFormat:@"%@/%@", NODEJS_PROJECT_RESOURCE_PATH, NODEJS_DLOPEN_OVERRIDE_FILENAME] ofType:@""];
// Check if the file to override dlopen lookup exists, for loading native modules from the Frameworks.
if(!dlopenoverridePath)
{
nodeArguments = [NSMutableArray arrayWithObjects:
@"node",
srcPath,
nil
];

[nodeArguments addObjectsFromArray:args];
} else {
nodeArguments = [NSMutableArray arrayWithObjects:
@"node",
@"-r",
dlopenoverridePath,
srcPath,
nil
];

[nodeArguments addObjectsFromArray:args];
}
[[NodeRunner sharedInstance] startEngineWithArguments:nodeArguments:nodePath];
}

RCT_EXPORT_METHOD(startNodeWithScript:(NSString *)script options:(NSDictionary *)options)
{
Expand Down Expand Up @@ -136,6 +172,23 @@ -(void)callStartNodeProject:(NSString *)mainFileName
}
}

RCT_EXPORT_METHOD(startNodeProjectWithArgs:(NSString *)command options:(NSDictionary *)options)
{
if(![NodeRunner sharedInstance].startedNodeAlready)
{
[NodeRunner sharedInstance].startedNodeAlready=true;
NSThread* nodejsThread = nil;
nodejsThread = [[NSThread alloc]
initWithTarget:self
selector:@selector(callStartNodeProjectWithArgs:)
object:command
];
// Set 2MB of stack space for the Node.js thread.
[nodejsThread setStackSize:2*1024*1024];
[nodejsThread start];
}
}

-(void) sendMessageBackToReact:(NSString*)channelName:(NSString*)message
{
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0), ^{
Expand Down