Skip to content

Commit

Permalink
napi: add test for exception handling implementation
Browse files Browse the repository at this point in the history
  • Loading branch information
Gabriel Schulhof committed Jan 20, 2017
1 parent 5cd6adc commit 0c96f22
Show file tree
Hide file tree
Showing 3 changed files with 100 additions and 0 deletions.
8 changes: 8 additions & 0 deletions test/addons-abi/test_exception/binding.gyp
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"targets": [
{
"target_name": "test_exception",
"sources": [ "test_exception.cc" ]
}
]
}
48 changes: 48 additions & 0 deletions test/addons-abi/test_exception/test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
'use strict';

var test_exception = require( "./build/Release/test_exception" );
var assert = require( "assert" );
var theError = new Error( "Some error" );
var throwTheError = function() {
throw theError;
};
var caughtError;

var throwNoError = function() {};

// Test that the native side successfully captures the exception
var returnedError = test_exception.returnException( throwTheError );
assert.strictEqual( theError, returnedError,
"Returned error is strictly equal to the thrown error" );

// Test that the native side passes the exception through
try {
test_exception.allowException( throwTheError );
} catch ( anError ) {
caughtError = anError;
}
assert.strictEqual( caughtError, theError,
"Thrown exception was allowed to pass through unhindered" );
caughtError = undefined;

// Test that the exception thrown above was marked as pending before it was handled on the JS side
assert.strictEqual( test_exception.wasPending(), true,
"VM was marked as having an exception pending when it was allowed through" );

// Test that the native side does not capture a non-existing exception
returnedError = test_exception.returnException( throwNoError );
assert.strictEqual( undefined, returnedError,
"Returned error is undefined when no exception is thrown" );

// Test that no exception appears that was not thrown by us
try {
test_exception.allowException( throwNoError );
} catch( anError ) {
caughtError = anError;
}
assert.strictEqual( undefined, caughtError,
"No exception originated on the native side" );

// Test that the exception state remains clear when no exception is thrown
assert.strictEqual( test_exception.wasPending(), false,
"VM was not marked as having an exception pending when none was allowed through" );
44 changes: 44 additions & 0 deletions test/addons-abi/test_exception/test_exception.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
#include <node_jsvmapi.h>
#include <node_api_helpers.h>

static bool exceptionWasPending = false;

NAPI_METHOD(returnException) {
napi_value jsFunction;

napi_get_cb_args(env, info, &jsFunction, 1);

// What is the return value when there was an exception?
napi_call_function(env, napi_get_global_scope(env), jsFunction, 0, 0);

napi_set_return_value(env, info, napi_get_and_clear_last_exception(env));
}

NAPI_METHOD(allowException) {
napi_value jsFunction;

napi_get_cb_args(env, info, &jsFunction, 1);

napi_call_function(env, napi_get_global_scope(env), jsFunction, 0, 0);

exceptionWasPending = napi_is_exception_pending(env);
}

NAPI_METHOD(wasPending) {
napi_set_return_value(env, info,
napi_create_boolean(env, exceptionWasPending));
}

NAPI_MODULE_INIT(Init) {
napi_set_property(env, exports,
napi_property_name(env, "returnException"),
napi_create_function(env, returnException));
napi_set_property(env, exports,
napi_property_name(env, "allowException"),
napi_create_function(env, allowException));
napi_set_property(env, exports,
napi_property_name(env, "wasPending"),
napi_create_function(env, wasPending));
}

NODE_MODULE_ABI(addon, Init)

0 comments on commit 0c96f22

Please sign in to comment.