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

Node-API migration #2305

Merged
merged 47 commits into from
Dec 11, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
47 commits
Select commit Hold shift + click to select a range
f61387d
Change dependency to napi
GazHank Aug 6, 2021
a604ed5
include napi
GazHank Aug 6, 2021
15058ef
update shared functionality to NAPI
GazHank Aug 6, 2021
0ec629f
win specific changes
GazHank Aug 7, 2021
2ab6d14
comment out async resources
GazHank Aug 7, 2021
fcdb5ea
initial mac changes for NAPI
GazHank Aug 7, 2021
f6651d6
Use include_dir instead of include
GazHank Aug 23, 2021
5dabafc
Remove unchecked call to napi_* for return args
GazHank Aug 23, 2021
b6e3d41
update unix methods to include napi_env
GazHank Aug 23, 2021
6b72730
Initial poller conversion (v broken)
GazHank Aug 23, 2021
c01113d
Fix setBaton (revert bug)
GazHank Aug 23, 2021
4350078
fix for include_dirs
GazHank Aug 24, 2021
8b37af1
Convert OpenBaton to AsyncWorker
GazHank Aug 24, 2021
d5b8185
SetError within Execute()
GazHank Aug 24, 2021
6118528
Replace napi_create_async_work for common methods
GazHank Sep 3, 2021
426d7e9
Comment update - AsyncResource -> AsyncWorker
GazHank Sep 3, 2021
03c4d7b
Update node-abi dependency
GazHank Sep 3, 2021
23e8629
fix Get
GazHank Sep 3, 2021
d5ec10b
Update List
GazHank Sep 3, 2021
5500e29
initial update of read and write (win)
GazHank Sep 3, 2021
7aac610
fix linux errors
GazHank Sep 3, 2021
deaea83
use void baton inheritance
GazHank Sep 4, 2021
c7c2b5c
Consistently pass callback to baton
GazHank Sep 5, 2021
7f3220b
Some poller patches
GazHank Sep 5, 2021
afb6371
remove redundant ByteSize Setting
GazHank Sep 8, 2021
5eebb78
fix typo
GazHank Sep 8, 2021
be974d9
NODE_ADDON_API_ENABLE_MAYBE
GazHank Sep 10, 2021
06c612d
some poller fixes
GazHank Sep 10, 2021
85635f8
reinstate setBaudRate
GazHank Sep 10, 2021
4e3d595
fix ConnectionOptionsBaton
GazHank Sep 10, 2021
82575c3
optional - remove warnings
GazHank Sep 10, 2021
a1cca06
Remove OnError logic
GazHank Sep 11, 2021
8383df4
Fix linting errors
GazHank Sep 11, 2021
1a09db0
linting errors part 2
GazHank Sep 11, 2021
57237f3
linting errors part 3
GazHank Sep 11, 2021
c051b7f
package updates
GazHank Sep 26, 2021
4bab582
enable exceptions
GazHank Sep 26, 2021
2ee143d
poller fixes
GazHank Sep 26, 2021
3ab5148
node-abi update
GazHank Sep 26, 2021
540da10
Low Latency fix
GazHank Sep 28, 2021
2bbd67a
package-lock fix
GazHank Sep 28, 2021
70a75b2
Revert loackfile to v1
GazHank Oct 10, 2021
64e8104
Cleanup OnError comments
GazHank Oct 10, 2021
42d87d1
Fix Windows Read and Write
GazHank Oct 10, 2021
3950949
Fix no COM port #2325
GazHank Oct 10, 2021
e0e9b52
fix locks
reconbot Nov 26, 2021
e300c78
fix: locks
reconbot Nov 26, 2021
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
5,751 changes: 2,392 additions & 3,359 deletions package-lock.json

Large diffs are not rendered by default.

7 changes: 4 additions & 3 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -27,20 +27,21 @@
},
"devDependencies": {
"cc": "^3.0.1",
"chai-subset": "^1.6.0",
"chai": "^4.3.4",
"chai-subset": "^1.5.0",
"codecov": "^3.8.3",
"eslint": "^8.2.0",
"eslint-config-prettier": "^8.3.0",
"eslint-plugin-import": "^2.25.3",
"eslint-plugin-mocha": "^9.0.0",
"eslint-plugin-node": "^11.1.0",
"eslint-plugin-prettier": "^4.0.0",
"eslint-plugin-promise": "^5.1.1",
"lerna": "^4.0.0",
"eslint": "^8.2.0",
"lerna-changelog": "^2.2.0",
"lerna": "^4.0.0",
"mocha": "^9.1.3",
"node-abi": "3.5.0",
"node-addon-api": "^4.2.0",
"nyc": "^15.1.0",
"plop": "^2.7.6",
"prebuild": "^11.0.0",
Expand Down
8 changes: 0 additions & 8 deletions packages/binding-mock/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

11 changes: 7 additions & 4 deletions packages/bindings/binding.gyp
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,11 @@
'sources': [
'src/serialport.cpp'
],
'include_dirs': [
'<!(node -e "require(\'nan\')")'
],
'include_dirs': ["<!(node -p \"require('node-addon-api').include_dir\")"],

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've always seen this setting as:

'include_dirs': ["<!@(node -p \"require('node-addon-api').include_dir\")"],

Specifically, the @ seems to be missing.

Note, dependencies generally doesn't use the @.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

'dependencies': ["<!(node -p \"require('node-addon-api').gyp\")"],
'cflags!': [ '-fno-exceptions' ],
'cflags_cc!': [ '-fno-exceptions' ],
"defines": ["NAPI_CPP_EXCEPTIONS"],
'conditions': [
['OS=="win"',
{
Expand All @@ -16,7 +18,7 @@
],
'msvs_settings': {
'VCCLCompilerTool': {
'ExceptionHandling': '2',
'ExceptionHandling': '1',
'DisableSpecificWarnings': [ '4530', '4506' ],
}
}
Expand All @@ -30,6 +32,7 @@
'src/darwin_list.cpp'
],
'xcode_settings': {
'GCC_ENABLE_CPP_EXCEPTIONS': 'YES',
'MACOSX_DEPLOYMENT_TARGET': '10.9',
'OTHER_LDFLAGS': [
'-framework CoreFoundation -framework IOKit'
Expand Down
24 changes: 12 additions & 12 deletions packages/bindings/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

17 changes: 10 additions & 7 deletions packages/bindings/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,8 @@
"@serialport/parser-readline": "9.2.4",
"bindings": "^1.5.0",
"debug": "^4.3.2",
"nan": "^2.15.0",
"prebuild-install": "^7.0.0"
"prebuild-install": "^7.0.0",
"node-addon-api": "4.2.0"
},
"devDependencies": {
"@serialport/binding-mock": "9.2.4",
Expand All @@ -21,11 +21,9 @@
"node": ">=10.0.0"
},
"scripts": {
"install": "prebuild-install --tag-prefix @serialport/bindings@ || node-gyp rebuild",
"install": "prebuild-install --tag-prefix @serialport/bindings@ --runtime napi --target 4 --verbose || node-gyp rebuild",
"lint": "cc --verbose",
"prebuild": "npm run prebuild-node && npm run prebuild-electron",
"prebuild-node": "prebuild --force --strip --verbose --tag-prefix @serialport/bindings@ -t 12.0.0 -t 14.0.0 -t 16.0.0",
"prebuild-electron": "prebuild --force --strip --verbose --tag-prefix @serialport/bindings@ -r electron -t 13.0.0 -t 14.0.0 -t 15.0.0 -t 16.0.0",
"prebuild": "prebuild --runtime napi --target 4 --force --strip --verbose --tag-prefix @serialport/bindings@",
"rebuild": "node-gyp rebuild"
},
"publishConfig": {
Expand All @@ -48,5 +46,10 @@
],
"linelength": "120"
},
"funding": "https://opencollective.com/serialport/donate"
"funding": "https://opencollective.com/serialport/donate",
"binary": {
"napi_versions": [
4
]
}
}
70 changes: 16 additions & 54 deletions packages/bindings/src/darwin_list.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,28 +16,28 @@
uv_mutex_t list_mutex;
Boolean lockInitialised = FALSE;

NAN_METHOD(List) {
Napi::Value List(const Napi::CallbackInfo& info) {
Napi::Env env = info.Env();
// callback
if (!info[0]->IsFunction()) {
Nan::ThrowTypeError("First argument must be a function");
return;
if (!info[0].IsFunction()) {
Napi::TypeError::New(env, "First argument must be a function").ThrowAsJavaScriptException();
return env.Null();
}

ListBaton* baton = new ListBaton();
Napi::Function callback = info[0].As<Napi::Function>();
ListBaton* baton = new ListBaton(callback);
snprintf(baton->errorString, sizeof(baton->errorString), "");
baton->callback.Reset(info[0].As<v8::Function>());

uv_work_t* req = new uv_work_t();
req->data = baton;
uv_queue_work(uv_default_loop(), req, EIO_List, (uv_after_work_cb)EIO_AfterList);
baton->Queue();
return env.Undefined();
}

void setIfNotEmpty(v8::Local<v8::Object> item, std::string key, const char *value) {
v8::Local<v8::String> v8key = Nan::New<v8::String>(key).ToLocalChecked();
void setIfNotEmpty(Napi::Object item, std::string key, const char *value) {
Napi::Env env = item.Env();
Napi::String v8key = Napi::String::New(env, key);
if (strlen(value) > 0) {
Nan::Set(item, v8key, Nan::New<v8::String>(value).ToLocalChecked());
(item).Set(v8key, Napi::String::New(env, value));
} else {
Nan::Set(item, v8key, Nan::Undefined());
(item).Set(v8key, env.Undefined());
}
}

Expand Down Expand Up @@ -271,8 +271,7 @@ static stDeviceListItem* GetSerialDevices() {
return devices;
}

void EIO_List(uv_work_t* req) {
ListBaton* data = static_cast<ListBaton*>(req->data);
void ListBaton::Execute() {

if (!lockInitialised) {
uv_mutex_init(&list_mutex);
Expand Down Expand Up @@ -304,7 +303,7 @@ void EIO_List(uv_work_t* req) {
if (*device.serialNumber) {
resultItem->serialNumber = device.serialNumber;
}
data->results.push_back(resultItem);
results.push_back(resultItem);

stDeviceListItem* current = next;

Expand All @@ -316,40 +315,3 @@ void EIO_List(uv_work_t* req) {
}
}
}

void EIO_AfterList(uv_work_t* req) {
Nan::HandleScope scope;

ListBaton* data = static_cast<ListBaton*>(req->data);

v8::Local<v8::Value> argv[2];
if (data->errorString[0]) {
argv[0] = v8::Exception::Error(Nan::New<v8::String>(data->errorString).ToLocalChecked());
argv[1] = Nan::Undefined();
} else {
v8::Local<v8::Array> results = Nan::New<v8::Array>();
int i = 0;
for (std::list<ListResultItem*>::iterator it = data->results.begin(); it != data->results.end(); ++it, i++) {
v8::Local<v8::Object> item = Nan::New<v8::Object>();

setIfNotEmpty(item, "path", (*it)->path.c_str());
setIfNotEmpty(item, "manufacturer", (*it)->manufacturer.c_str());
setIfNotEmpty(item, "serialNumber", (*it)->serialNumber.c_str());
setIfNotEmpty(item, "pnpId", (*it)->pnpId.c_str());
setIfNotEmpty(item, "locationId", (*it)->locationId.c_str());
setIfNotEmpty(item, "vendorId", (*it)->vendorId.c_str());
setIfNotEmpty(item, "productId", (*it)->productId.c_str());

Nan::Set(results, i, item);
}
argv[0] = Nan::Null();
argv[1] = results;
}
data->callback.Call(2, argv, data);

for (std::list<ListResultItem*>::iterator it = data->results.begin(); it != data->results.end(); ++it) {
delete *it;
}
delete data;
delete req;
}
38 changes: 30 additions & 8 deletions packages/bindings/src/darwin_list.h
Original file line number Diff line number Diff line change
@@ -1,15 +1,15 @@
#ifndef PACKAGES_SERIALPORT_SRC_DARWIN_LIST_H_
#define PACKAGES_SERIALPORT_SRC_DARWIN_LIST_H_
#include <sys/param.h> // For MAXPATHLEN
#include <nan.h>
#include <napi.h>
#include <uv.h>
#include <list>
#include <string>

#define ERROR_STRING_SIZE 1024
#define ERROR_STRING_SIZE 1088

NAN_METHOD(List);
void EIO_List(uv_work_t* req);
void EIO_AfterList(uv_work_t* req);
Napi::Value List(const Napi::CallbackInfo& info);
void setIfNotEmpty(Napi::Object item, std::string key, const char *value);

struct ListResultItem {
std::string path;
Expand All @@ -21,11 +21,33 @@ struct ListResultItem {
std::string productId;
};

struct ListBaton : public Nan::AsyncResource {
ListBaton() : AsyncResource("node-serialport:ListBaton"), errorString() {}
Nan::Callback callback;
struct ListBaton : public Napi::AsyncWorker {
ListBaton(Napi::Function& callback) : Napi::AsyncWorker(callback, "node-serialport:ListBaton"),
errorString() {}
std::list<ListResultItem*> results;
char errorString[ERROR_STRING_SIZE];
void Execute() override;

void OnOK() override {
Napi::Env env = Env();
Napi::HandleScope scope(env);
Napi::Array result = Napi::Array::New(env);
int i = 0;
for (std::list<ListResultItem*>::iterator it = results.begin(); it != results.end(); ++it, i++) {
Napi::Object item = Napi::Object::New(env);

setIfNotEmpty(item, "path", (*it)->path.c_str());
setIfNotEmpty(item, "manufacturer", (*it)->manufacturer.c_str());
setIfNotEmpty(item, "serialNumber", (*it)->serialNumber.c_str());
setIfNotEmpty(item, "pnpId", (*it)->pnpId.c_str());
setIfNotEmpty(item, "locationId", (*it)->locationId.c_str());
setIfNotEmpty(item, "vendorId", (*it)->vendorId.c_str());
setIfNotEmpty(item, "productId", (*it)->productId.c_str());

(result).Set(i, item);
}
Callback().Call({env.Null(), result});
}
};

typedef struct SerialDevice {
Expand Down
Loading