N-API
N-API (произносится как N, за которым следует API) — это API для создания нативных дополнений. Он независим от базовой среды JavaScript (например, V8) и поддерживается как часть самого Node.js. Это API с гарантированной стабильностью двоичного интерфейса (ABI) между версиями Node.js. Он предназначен для защиты дополнений от изменений в базовом движке JavaScript и позволяет модулям, скомпилированным для одной основной версии, работать в более поздних основных версиях Node.js без перекомпиляции. Руководство по стабильности ABI предоставляет более подробное объяснение.
Дополнения создаются/упаковываются с помощью того же подхода/инструментов, что и в разделе, озаглавленном C++ дополнения. Единственное отличие — набор API, используемых нативным кодом. Вместо использования V8 или Native Abstractions for Node.js API, используются функции, доступные в N-API.
API, экспонируемые N-API, как правило, используются для создания и управления значениями JavaScript. Понятия и операции, как правило, соответствуют идеям, указанным в спецификации языка ECMA262. API обладают следующими свойствами:
- Все вызовы N-API возвращают код состояния типа
napi_status. Этот код указывает, был ли вызов API успешным или неудачным. - Значение возврата API передается через параметр-результат.
- Все значения JavaScript абстрагированы за неявным типом, названным
napi_value. - В случае кода состояния ошибки дополнительная информация может быть получена с помощью
napi_get_last_error_info. Более подробная информация доступна в разделе обработки ошибок Обработка ошибок.
N-API — это C API, обеспечивающий стабильность ABI между версиями Node.js и различными уровнями компиляторов. C++ API может быть проще в использовании. Для поддержки использования C++, проект поддерживает модуль обёртки на C++ под названием node-addon-api. Этот модуль предоставляет встроенный C++ API. Бинарные файлы, созданные с помощью node-addon-api, будут зависеть от символов функций N-API, основанных на C, экспортируемых Node.js. node-addon-api — это более эффективный способ написания кода, вызывающего N-API. Например, рассмотрим следующий node-addon-api код. Первая секция показывает node-addon-api код, а вторая секция показывает, что фактически используется в дополнении.
Object obj = Object::New(env); obj["foo"] = String::New(env, "bar");
napi_status status;
napi_value object, string;
status = napi_create_object(env, &object);
if (status != napi_ok) {
napi_throw_error(env, ...);
return;
}
status = napi_create_string_utf8(env, "bar", NAPI_AUTO_LENGTH, &string);
if (status != napi_ok) {
napi_throw_error(env, ...);
return;
}
status = napi_set_named_property(env, object, "foo", string);
if (status != napi_ok) {
napi_throw_error(env, ...);
return;
}
В итоге, дополнение использует только экспортированные C API. В результате, оно по-прежнему получает преимущества стабильности ABI, предоставляемые C API.
При использовании node-addon-api вместо C API, начните с документации API docs для node-addon-api.
Последствия стабильности ABI
Хотя N-API гарантирует стабильность ABI, другие части Node.js не гарантируют её, и любые внешние библиотеки, используемые из дополнения, могут тоже не гарантировать её. В частности, ни один из следующих API не гарантирует стабильность ABI между основными версиями:
-
API Node.js на C++, доступные через любой из
#include <node.h> #include <node_buffer.h> #include <node_version.h> #include <node_object_wrap.h>
-
API libuv, которые также включены в Node.js и доступны через
#include <uv.h>
-
API V8, доступный через
#include <v8.h>
Таким образом, для того, чтобы дополнение оставалось совместимым с ABI между основными версиями Node.js, оно должно использовать исключительно N-API, ограничивая себя использованием
#include <node_api.h>
и проверяя для всех используемых внешних библиотек, что эти библиотеки обеспечивают гарантии стабильности ABI, подобные N-API.
Использование
Для использования функций N-API, включите файл node_api.h, который находится в каталоге src в дереве разработки Node:
#include <node_api.h>
Это включит по умолчанию NAPI_VERSION для данной версии Node.js. Для обеспечения совместимости со специфичными версиями N-API, версию можно указать явно при включении заголовка:
#define NAPI_VERSION 3 #include <node_api.h>
Это ограничит поверхность N-API только функциональностью, которая была доступна в указанных (и более ранних) версиях.
Некоторая часть поверхности N-API считается экспериментальной и требует явного включения для доступа к этим API:
#define NAPI_EXPERIMENTAL #include <node_api.h>
В этом случае вся поверхность API, включая любые экспериментальные API, будет доступна коду модуля.
Матрица версий N-API
| 1 | 2 | 3 | 4 | 5 | |
|---|---|---|---|---|---|
| v6.x | v6.14.2* | ||||
| v8.x | v8.0.0* | v8.10.0* | v8.11.2 | ||
| v9.x | v9.0.0* | v9.3.0* | v9.11.0* | ||
| v10.x | v10.0.0 | v10.16.0 | v10.17.0 | ||
| v11.x | v11.0.0 | v11.8.0 | |||
| v12.x | v12.0.0 | ||||
| v13.x |
* Указывает, что версия N-API была выпущена как экспериментальная
API жизненного цикла среды
Раздел 8.7 спецификации языка ECMAScript определяет понятие "Agent" как автономную среду, в которой выполняется код JavaScript. Несколько таких Agent могут быть запущены и завершены как одновременно, так и последовательно процессом.
Среда Node.js соответствует ECMAScript Agent. В основном процессе среда создается при запуске, а дополнительные среды могут быть созданы на отдельных потоках, чтобы служить потоками-рабочими нитями. Когда Node.js встроен в другое приложение, основной поток приложения также может создавать и уничтожать среду Node.js несколько раз в течение жизненного цикла процесса приложения, таким образом, каждая среда Node.js, созданная приложением, может в свою очередь, в течение своего жизненного цикла создавать и уничтожать дополнительные среды как рабочие потоки.
С точки зрения нативного дополнения это означает, что предоставляемые им связи могут вызываться несколько раз, из нескольких контекстов и даже одновременно из нескольких потоков.
Нативным дополнениям может потребоваться выделять глобальное состояние, которым они пользуются на протяжении всего жизненного цикла, таким образом, состояние должно быть уникальным для каждого экземпляра дополнения.
Для этой среды N-API предоставляет способ выделения данных, таким образом, что его жизненный цикл привязан к жизненному циклу Agent.
napi_set_instance_data
napi_status napi_set_instance_data(napi_env env,
void* data,
napi_finalize finalize_cb,
void* finalize_hint);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] data: Элемент данных, который необходимо сделать доступным для связей этого экземпляра. -
[in] finalize_cb: Функция, которая вызывается при разборке среды. Функция получаетdata, чтобы иметь возможность освободить его. -
[in] finalize_hint: Необязательный подсказчик для передачи в обратный вызов finalization во время сбора мусора.
Возвращает napi_ok в случае успеха API.
Этот API ассоциирует data с текущим работающим Agent. data может быть позже получен с помощью napi_get_instance_data(). Любые существующие данные, ассоциированные с текущим работающим Agent, которые были установлены посредством предыдущего вызова napi_set_instance_data(), будут перезаписаны. Если обратный вызов finalize_cb был предоставлен предыдущим вызовом, он не будет вызван.
napi_get_instance_data
napi_status napi_get_instance_data(napi_env env,
void** data);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[out] data: Элемент данных, который ранее был связан с текущим работающим Agent посредством вызоваnapi_set_instance_data().
Возвращает napi_ok в случае успеха API.
Этот API извлекает данные, которые были ранее связаны с текущим работающим Agent через napi_set_instance_data(). Если данные не установлены, вызов будет успешным, и data будет установлено в NULL.
Основные типы данных N-API
N-API экспонирует следующие фундаментальные типы данных как абстракции, используемые различными API. Эти API следует рассматривать как неявные, интроспекция возможна только с помощью других вызовов N-API.
napi_status
Целочисленный код состояния, указывающий на успех или неудачу вызова N-API. В настоящее время поддерживаются следующие коды состояния.
typedef enum {
napi_ok,
napi_invalid_arg,
napi_object_expected,
napi_string_expected,
napi_name_expected,
napi_function_expected,
napi_number_expected,
napi_boolean_expected,
napi_array_expected,
napi_generic_failure,
napi_pending_exception,
napi_cancelled,
napi_escape_called_twice,
napi_handle_scope_mismatch,
napi_callback_scope_mismatch,
napi_queue_full,
napi_closing,
napi_bigint_expected,
napi_date_expected,
napi_arraybuffer_expected,
napi_detachable_arraybuffer_expected,
} napi_status;
Если требуется дополнительная информация при возврате API неудачного состояния, её можно получить, вызвав napi_get_last_error_info.
napi_extended_error_info
typedef struct {
const char* error_message;
void* engine_reserved;
uint32_t engine_error_code;
napi_status error_code;
} napi_extended_error_info;
-
error_message: Строка в кодировке UTF8, содержащая VM-нейтральное описание ошибки. -
engine_reserved: Зарезервировано для VM-специфичных деталей ошибки. В настоящее время не реализовано ни для одного VM. -
engine_error_code: VM-специфический код ошибки. В настоящее время не реализовано ни для одного VM. -
error_code: Код состояния N-API, являющийся источником последней ошибки.
См. раздел Обработка ошибок для дополнительной информации.
napi_env
napi_env используется для представления контекста, который базовая реализация N-API может использовать для сохранения VM-специфичного состояния. Эта структура передаётся нативным функциям при их вызове, и её необходимо передавать обратно при выполнении вызовов N-API. Конкретно, тот же napi_env объект, который был передан при вызове начальной нативной функции, должен передаваться во все последующие вложенные вызовы N-API. Кэширование napi_env для целей общего повторного использования запрещено.
napi_value
Это неявный указатель, используемый для представления значения JavaScript.
napi_threadsafe_function
Это неявный указатель, представляющий функцию JavaScript, которая может вызываться асинхронно из нескольких потоков с помощью napi_call_threadsafe_function().
napi_threadsafe_function_release_mode
Значение, которое следует передать napi_release_threadsafe_function(), чтобы указать, должна ли функция многопоточного доступа закрываться немедленно (napi_tsfn_abort) или просто быть освобождена (napi_tsfn_release) и, таким образом, быть доступной для последующего использования через napi_acquire_threadsafe_function() и napi_call_threadsafe_function().
typedef enum {
napi_tsfn_release,
napi_tsfn_abort
} napi_threadsafe_function_release_mode;
napi_threadsafe_function_call_mode
Значение, передаваемое napi_call_threadsafe_function(), чтобы указать, следует ли блокировать вызов при переполнении очереди, связанной с функцией многопоточного доступа.
typedef enum {
napi_tsfn_nonblocking,
napi_tsfn_blocking
} napi_threadsafe_function_call_mode;
Типы управления памятью N-API
napi_handle_scope
Это абстракция, используемая для управления и изменения срока службы объектов, созданных в конкретной области видимости. В общем случае значения N-API создаются в контексте области видимости handle. Когда из JavaScript вызывается метод нативного кода, существует область видимости handle по умолчанию. Если пользователь явно не создает новую область видимости handle, значения N-API будут созданы в области видимости handle по умолчанию. Для любого вызова кода за пределами выполнения метода нативного кода (например, во время вызова обратного вызова libuv) модуль должен создать область видимости перед вызовом функций, которые могут привести к созданию значений JavaScript.
Области видимости handle создаются с помощью napi_open_handle_scope и уничтожаются с помощью napi_close_handle_scope. Закрытие области видимости может указывать сборщику мусора, что все napi_value, созданные в течение срока службы области видимости handle, больше не ссылаются из текущей области видимости стека.
Для получения более подробной информации см. Управление жизненным циклом объектов.
napi_escapable_handle_scope
Области видимости handle с возможностью передачи — это особый тип областей видимости handle для возврата значений, созданных в рамках определённой области видимости handle в родительскую область видимости.
napi_ref
Это абстракция, используемая для ссылки на napi_value. Это позволяет пользователям управлять жизненным циклом значений JavaScript, включая явное определение минимального срока их существования.
Для получения более подробной информации см. Управление жизненным циклом объектов.
Типы обратных вызовов N-API
napi_callback_info
Неявной тип данных, передаваемый функции обратного вызова. Он может использоваться для получения дополнительной информации о контексте, в котором был вызван обратный вызов.
napi_callback
Тип указателя на функцию для предоставленных пользователем нативных функций, которые должны быть экспонированы для JavaScript через N-API. Функции обратного вызова должны соответствовать следующей сигнатуре:
typedef napi_value (*napi_callback)(napi_env, napi_callback_info);
napi_finalize
Тип указателя на функцию, предоставляемую плагином, которая позволяет пользователю получать уведомления о том, когда данные, принадлежащие внешнему источнику, готовы к очистке, поскольку объект, с которым они были связаны, был собран сборщиком мусора. Пользователь должен предоставить функцию, удовлетворяющую следующей сигнатуре, которая будет вызвана при сборе объекта. В настоящее время, napi_finalize может использоваться для определения того, когда собираются объекты, имеющие внешние данные.
typedef void (*napi_finalize)(napi_env env,
void* finalize_data,
void* finalize_hint);
napi_async_execute_callback
Указатель на функцию, используемый с функциями, поддерживающими асинхронные операции. Функции обратного вызова должны удовлетворять следующей сигнатуре:
typedef void (*napi_async_execute_callback)(napi_env env, void* data);
Реализации этого типа функций должны избегать выполнения любых вызовов N-API, которые могут привести к выполнению JavaScript или взаимодействию с объектами JavaScript. Чаще всего любой код, которому необходимо сделать вызовы N-API, следует выполнять в napi_async_complete_callback.
napi_async_complete_callback
Указатель на функцию, используемый с функциями, поддерживающими асинхронные операции. Функции обратного вызова должны удовлетворять следующей сигнатуре:
typedef void (*napi_async_complete_callback)(napi_env env,
napi_status status,
void* data);
napi_threadsafe_function_call_js
Указатель на функцию, используемую с асинхронными многопоточными вызовами функций. Обратный вызов будет вызван в главном потоке. Его цель — использовать элемент данных, поступающий через очередь из одного из вторичных потоков, для построения параметров, необходимых для вызова в JavaScript, обычно через napi_call_function, а затем сделать вызов в JavaScript.
Данные, поступающие из вторичного потока через очередь, передаются в параметре data, а функция JavaScript, которую нужно вызвать, передаётся в параметре js_callback.
N-API устанавливает среду перед вызовом этого обратного вызова, поэтому достаточно вызвать функцию JavaScript через napi_call_function, а не через napi_make_callback.
Функции обратного вызова должны удовлетворять следующей сигнатуре:
typedef void (*napi_threadsafe_function_call_js)(napi_env env,
napi_value js_callback,
void* context,
void* data);
-
[in] env: Среда для использования в вызовах API илиNULL, если функция многопоточного доступа закрывается иdataможет потребоваться освободить. -
[in] js_callback: Функция JavaScript для вызова илиNULL, если функция многопоточного доступа закрывается иdataможет потребоваться освободить. Она также может бытьNULL, если функция многопоточного доступа была создана безjs_callback. -
[in] context: Необязательные данные, с которыми была создана функция многопоточного доступа. -
[in] data: Данные, созданные вторичным потоком. Ответственность обратного вызова заключается в преобразовании этих нативных данных в значения JavaScript (с помощью функций N-API), которые могут быть переданы в качестве параметров при вызовеjs_callback. Этот указатель управляется исключительно потоками и этим обратным вызовом. Следовательно, этот обратный вызов должен освободить данные.
Обработка ошибок
N-API использует как возвращаемые значения, так и исключения JavaScript для обработки ошибок. В следующих разделах объясняется подход для каждого случая.
Возвращаемые значения
Все функции N-API используют один и тот же шаблон обработки ошибок. Тип возвращаемого значения всех функций API — napi_status.
Возвращаемое значение будет napi_ok, если запрос был выполнен успешно и не было брошено ни одного необработанного исключения JavaScript. Если произошла ошибка И было брошено исключение, то возвращается значение napi_status для ошибки. Если было брошено исключение, но ошибка не произошла, возвращается napi_pending_exception.
В тех случаях, когда возвращается значение, отличное от napi_ok или napi_pending_exception, необходимо вызвать napi_is_exception_pending для проверки наличия ожидаемого исключения. Более подробная информация приведена в разделе об исключениях.
Полный набор возможных значений napi_status определён в napi_api_types.h.
Возвращаемое значение napi_status предоставляет независимое от виртуальной машины представление возникшей ошибки. В некоторых случаях полезно получить более подробную информацию, включая строку, представляющую ошибку, а также информацию, специфичную для виртуальной машины (движка).
Для получения этой информации предоставляется napi_get_last_error_info, которая возвращает структуру napi_extended_error_info.
Формат структуры napi_extended_error_info следующий:
typedef struct napi_extended_error_info {
const char* error_message;
void* engine_reserved;
uint32_t engine_error_code;
napi_status error_code;
};
-
error_message: Текстовое представление возникшей ошибки. -
engine_reserved: Неявный дескриптор, зарезервированный только для использования движком. -
engine_error_code: Код ошибки, специфичный для виртуальной машины. -
error_code: Код состояния n-api для последней ошибки.
napi_get_last_error_info возвращает информацию о последнем выполненном вызове N-API.
Не полагайтесь на содержимое или формат любой расширенной информации, так как она не подчиняется SemVer и может измениться в любое время. Она предназначена только для целей ведения журнала.
napi_get_last_error_info
napi_status
napi_get_last_error_info(napi_env env,
const napi_extended_error_info** result);
-
[in] env: Среда, в которой вызывается API. -
[out] result: Структураnapi_extended_error_infoс более подробной информацией об ошибке.
Возвращает napi_ok, если API выполнена успешно.
Этот API извлекает структуру napi_extended_error_info с информацией о последней произошедшей ошибке.
Содержимое возвращаемой структуры napi_extended_error_info действительно только до тех пор, пока функция n-api не будет вызвана в той же env.
Не полагайтесь на содержимое или формат любой расширенной информации, так как она не подчиняется SemVer и может измениться в любое время. Она предназначена только для целей ведения журнала.
Этот API может быть вызван, даже если ожидается исключение JavaScript.
Исключения
Любой вызов функции N-API может привести к возникновению ожидаемого исключения JavaScript. Это очевидно для любой функции, которая может вызвать выполнение JavaScript, но N-API определяет, что исключение может быть ожидаемым при возврате из любой функции API.
Если возвращаемое значение napi_status функции — napi_ok, значит, исключение не ожидается, и дополнительных действий не требуется. Если возвращаемое значение napi_status отличается от napi_ok или napi_pending_exception, чтобы попытаться восстановиться и продолжить вместо немедленного возврата, необходимо вызвать napi_is_exception_pending для определения наличия ожидаемого исключения.
Во многих случаях, когда вызывается функция N-API, и уже ожидается исключение, функция вернётся немедленно с napi_status от napi_pending_exception. Однако, это не относится ко всем функциям. N-API позволяет вызывать подмножество функций, чтобы выполнить некоторую минимальную очистку перед возвратом в JavaScript. В этом случае napi_status отобразит статус для функции. Он не будет отражать предыдущие ожидающие исключения. Для избежания путаницы, проверяйте состояние ошибки после каждого вызова функции.
Когда ожидается исключение, можно использовать один из двух подходов.
Первый подход заключается в выполнении необходимой очистки, а затем возврате, чтобы управление вернулось в JavaScript. В рамках перехода обратно в JavaScript исключение будет сгенерировано в точке кода JavaScript, где был вызван метод нативного кода. Поведение большинства вызовов N-API не определено, пока ожидается исключение, и многие просто вернут napi_pending_exception, поэтому важно сделать как можно меньше и затем вернуться в JavaScript, где исключение может быть обработано.
Второй подход заключается в попытке обработать исключение. Будут случаи, когда нативный код может поймать исключение, выполнить соответствующее действие и продолжить. Это рекомендуется только в определённых случаях, когда известно, что исключение можно безопасно обработать. В таких случаях можно использовать napi_get_and_clear_last_exception, чтобы получить и очистить исключение. При успехе, результат будет содержать дескриптор последнего сгенерированного исключения в JavaScript Object . Если после получения исключения выяснится, что его нельзя обработать, его можно повторно сгенерировать с помощью napi_throw, где error — объект JavaScript Error , который нужно сгенерировать.
Также доступны следующие служебные функции, в случае необходимости генерации исключений или проверки, является ли napi_value экземпляром объекта JavaScript Error в нативном коде: napi_throw_error, napi_throw_type_error, napi_throw_range_error и napi_is_error.
Также доступны следующие служебные функции для создания объекта Error в нативном коде: napi_create_error, napi_create_type_error и napi_create_range_error, где результат — napi_value , который ссылается на созданный объект JavaScript Error .
Проект Node.js добавляет коды ошибок ко всем ошибкам, генерируемым внутри. Цель состоит в том, чтобы приложения использовали эти коды ошибок для проверки всех ошибок. Соответствующие сообщения об ошибках останутся, но будут использоваться только для ведения журнала и отображения, с ожиданием, что сообщение может измениться без применения SemVer. Для поддержки этой модели в N-API, как в внутренней функциональности, так и в функциональности конкретного модуля (что является хорошей практикой), функции throw_ и create_ принимают необязательный параметр code, который представляет строку кода, добавляемую в объект ошибки. Если необязательный параметр равен NULL, код к ошибке не добавляется. Если код предоставлен, имя, связанное с ошибкой, также обновляется следующим образом:
originalName [code]
где originalName — исходное имя, связанное с ошибкой, а code — предоставленный код. Например, если код 'ERR_ERROR_1' и создаётся TypeError, имя будет:
TypeError [ERR_ERROR_1]
napi_throw
NAPI_EXTERN napi_status napi_throw(napi_env env, napi_value error);
-
[in] env: Окружение, в котором вызывается API. -
[in] error: Значение JavaScript, которое необходимо сгенерировать.
Возвращает napi_ok если API успешно выполнен.
Этот API генерирует исключение с предоставленным значением JavaScript.
napi_throw_error
NAPI_EXTERN napi_status napi_throw_error(napi_env env,
const char* code,
const char* msg);
-
[in] env: Окружение, в котором вызывается API. -
[in] code: Необязательный код ошибки, который необходимо установить для ошибки. -
[in] msg: Строка C, представляющая текст, который необходимо связать с ошибкой.
Возвращает napi_ok если API успешно выполнен.
Этот API генерирует исключение JavaScript Error с предоставленным текстом.
napi_throw_type_error
NAPI_EXTERN napi_status napi_throw_type_error(napi_env env,
const char* code,
const char* msg);
-
[in] env: Окружение, в котором вызывается API. -
[in] code: Необязательный код ошибки, который необходимо установить для ошибки. -
[in] msg: Строка C, представляющая текст, который необходимо связать с ошибкой.
Возвращает napi_ok если API успешно выполнен.
Этот API генерирует исключение JavaScript TypeError с предоставленным текстом.
napi_throw_range_error
NAPI_EXTERN napi_status napi_throw_range_error(napi_env env,
const char* code,
const char* msg);
-
[in] env: Окружение, в котором вызывается API. -
[in] code: Необязательный код ошибки, который необходимо установить для ошибки. -
[in] msg: Строка C, представляющая текст, который необходимо связать с ошибкой.
Возвращает napi_ok если API успешно выполнен.
Этот API генерирует исключение JavaScript RangeError с предоставленным текстом.
napi_is_error
NAPI_EXTERN napi_status napi_is_error(napi_env env,
napi_value value,
bool* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] value:napi_valueдля проверки. -
[out] result: Булево значение, которое устанавливается в true, еслиnapi_valueпредставляет ошибку, в противном случае false.
Возвращает napi_ok если API успешно выполнен.
Этот API проверяет napi_value на то, является ли он объектом ошибки.
napi_create_error
NAPI_EXTERN napi_status napi_create_error(napi_env env,
napi_value code,
napi_value msg,
napi_value* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] code: Необязательный код с строкой для кода ошибки, который необходимо связать с ошибкой. -
[in] msg:napi_value, ссылающийся на объект JavaScriptString, который будет использоваться как сообщение дляError. -
[out] result:napi_value, представляющий созданную ошибку.
Возвращает napi_ok если API успешно выполнен.
Этот API возвращает объект JavaScript Error с предоставленным текстом.
napi_create_type_error
NAPI_EXTERN napi_status napi_create_type_error(napi_env env,
napi_value code,
napi_value msg,
napi_value* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] code: Необязательный код с строкой для кода ошибки, который необходимо связать с ошибкой. -
[in] msg:napi_value, ссылающийся на объект JavaScriptString, который будет использоваться как сообщение дляError. -
[out] result:napi_value, представляющий созданную ошибку.
Возвращает napi_ok если API успешно выполнен.
Этот API возвращает объект JavaScript TypeError с предоставленным текстом.
napi_create_range_error
NAPI_EXTERN napi_status napi_create_range_error(napi_env env,
napi_value code,
napi_value msg,
napi_value* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] code: Необязательный код с строкой для кода ошибки, который необходимо связать с ошибкой. -
[in] msg:napi_value, ссылающийся на объект JavaScriptString, который будет использоваться как сообщение дляError. -
[out] result:napi_value, представляющий созданную ошибку.
Возвращает napi_ok если API успешно выполнен.
Этот API возвращает объект JavaScript RangeError с предоставленным текстом.
napi_get_and_clear_last_exception
napi_status napi_get_and_clear_last_exception(napi_env env,
napi_value* result);
-
[in] env: Окружение, в котором вызывается API. -
[out] result: Исключение, если оно ожидается, NULL в противном случае.
Возвращает napi_ok если API успешно выполнен.
Этот API возвращает true, если ожидается исключение.
Этот API может быть вызван даже если ожидается исключение JavaScript.
napi_is_exception_pending
napi_status napi_is_exception_pending(napi_env env, bool* result);
-
[in] env: Окружение, в котором вызывается API. -
[out] result: Булево значение, которое устанавливается в true, если ожидается исключение.
Возвращает napi_ok если API успешно выполнен.
Этот API возвращает true, если ожидается исключение.
Этот API может быть вызван даже если ожидается исключение JavaScript.
napi_fatal_exception
napi_status napi_fatal_exception(napi_env env, napi_value err);
-
[in] env: Окружение, в котором вызывается API. -
[in] err: Ошибка, передаваемая в'uncaughtException'.
Вызывает 'uncaughtException' в JavaScript. Полезно, если асинхронный обработчик выбрасывает исключение без возможности восстановления.
Критические ошибки
В случае невосстановимой ошибки в нативном модуле, может быть сгенерирована критическая ошибка для немедленного завершения процесса.
napi_fatal_error
NAPI_NO_RETURN void napi_fatal_error(const char* location,
size_t location_len,
const char* message,
size_t message_len);
-
[in] location: Необязательное место, где произошла ошибка. -
[in] location_len: Длина места в байтах, илиNAPI_AUTO_LENGTHесли она с нулевым окончанием. -
[in] message: Сообщение, связанное с ошибкой. -
[in] message_len: Длина сообщения в байтах, илиNAPI_AUTO_LENGTHесли оно с нулевым окончанием.
Вызов функции не возвращает значения, процесс будет завершен.
К этому API можно обратиться, даже если есть ожидающее выполнение исключение JavaScript.
Управление жизненным циклом объектов
При выполнении вызовов N-API могут возвращаться дескрипторы объектов в куче для базовой виртуальной машины в виде napi_values. Эти дескрипторы должны удерживать объекты «живыми» до тех пор, пока они больше не требуются кодом нативном языке, иначе объекты могут быть собраны сборщиком мусора до завершения их использования кодом нативном языке.
При возвращении дескрипторов объектов они связываются со «степенью видимости». Срок жизни по умолчанию связан со сроком жизни вызова нативного метода. В результате по умолчанию дескрипторы остаются валидными, и объекты, связанные с этими дескрипторами, будут удерживаться живыми в течение срока жизни вызова нативного метода.
Однако во многих случаях необходимо, чтобы дескрипторы оставались валидными как короче, так и дольше, чем срок жизни нативного метода. В следующих разделах описаны функции N-API, которые можно использовать для изменения срока жизни дескриптора от значения по умолчанию.
Уменьшение срока жизни дескриптора по сравнению со сроком жизни нативного метода
Часто необходимо уменьшить срок жизни дескрипторов по сравнению со сроком жизни нативного метода. Например, рассмотрим нативный метод, у которого есть цикл, перебирающий элементы в большом массиве:
for (int i = 0; i < 1000000; i++) {
napi_value result;
napi_status status = napi_get_element(env, object, i, &result);
if (status != napi_ok) {
break;
}
// do something with element
}
Это приведет к созданию большого количества дескрипторов, что приведет к значительному расходу ресурсов. Кроме того, даже если код нативном языке может использовать только последний дескриптор, все связанные объекты также будут оставаться живыми, так как они все принадлежат одной и той же области видимости.
Для решения этой проблемы N-API предоставляет возможность создания новой «области видимости», к которой будут привязаны вновь созданные дескрипторы. После того, как эти дескрипторы больше не потребуются, область видимости можно «закрыть», и все дескрипторы, связанные с этой областью видимости, станут невалидными. Доступные методы для открытия/закрытия областей видимости — napi_open_handle_scope и napi_close_handle_scope.
N-API поддерживает только одну вложенную иерархию областей видимости. В любое время активна только одна область видимости, и все новые дескрипторы будут привязаны к этой области видимости, пока она активна. Области видимости должны закрываться в обратном порядке их открытия. Кроме того, все области видимости, созданные в рамках нативного метода, должны быть закрыты перед возвратом из этого метода.
Рассмотрим предыдущий пример, добавление вызовов napi_open_handle_scope и napi_close_handle_scope гарантирует, что не более одного дескриптора будет валидным в течение всего цикла:
for (int i = 0; i < 1000000; i++) {
napi_handle_scope scope;
napi_status status = napi_open_handle_scope(env, &scope);
if (status != napi_ok) {
break;
}
napi_value result;
status = napi_get_element(env, object, i, &result);
if (status != napi_ok) {
break;
}
// do something with element
status = napi_close_handle_scope(env, scope);
if (status != napi_ok) {
break;
}
}
При вложенности областей видимости существуют случаи, когда дескриптор из внутренней области видимости должен существовать дольше, чем срок жизни этой области видимости. N-API поддерживает «избегаемую область видимости», чтобы справиться с этим случаем. Избегаемая область видимости позволяет продвинуть один дескриптор, чтобы он «вышел» из текущей области видимости, и срок жизни дескриптора изменится с текущей области видимости на внешнюю.
Доступные методы для открытия/закрытия избегаемых областей видимости — napi_open_escapable_handle_scope и napi_close_escapable_handle_scope.
Запрос на продвижение дескриптора выполняется с помощью napi_escape_handle, который можно вызвать только один раз.
napi_open_handle_scope
NAPI_EXTERN napi_status napi_open_handle_scope(napi_env env,
napi_handle_scope* result);
-
[in] env: Среда, в которой вызывается API. -
[out] result:napi_valueпредставляющая новую область видимости.
Возвращает napi_ok в случае успешного выполнения API.
Этот API открывает новую область видимости.
napi_close_handle_scope
NAPI_EXTERN napi_status napi_close_handle_scope(napi_env env,
napi_handle_scope scope);
-
[in] env: Среда, в которой вызывается API. -
[in] scope:napi_valueпредставляющая область видимости для закрытия.
Возвращает napi_ok в случае успешного выполнения API.
Этот API закрывает переданную область видимости. Области видимости должны закрываться в обратном порядке их создания.
К этому API можно обратиться, даже если есть ожидающее выполнение исключение JavaScript.
napi_open_escapable_handle_scope
NAPI_EXTERN napi_status
napi_open_escapable_handle_scope(napi_env env,
napi_handle_scope* result);
-
[in] env: Среда, в которой вызывается API. -
[out] result:napi_valueпредставляющая новую область видимости.
Возвращает napi_ok в случае успешного выполнения API.
Этот API открывает новую область видимости, из которой один объект может быть продвинут во внешнюю область видимости.
napi_close_escapable_handle_scope
NAPI_EXTERN napi_status
napi_close_escapable_handle_scope(napi_env env,
napi_handle_scope scope);
-
[in] env: Среда, в которой вызывается API. -
[in] scope:napi_valueпредставляющая область видимости для закрытия.
Возвращает napi_ok в случае успешного выполнения API.
Этот API закрывает переданную область видимости. Области видимости должны закрываться в обратном порядке их создания.
К этому API можно обратиться, даже если есть ожидающее выполнение исключение JavaScript.
napi_escape_handle
napi_status napi_escape_handle(napi_env env,
napi_escapable_handle_scope scope,
napi_value escapee,
napi_value* result);
-
[in] env: Среда, в которой вызывается API. -
[in] scope:napi_valueпредставляющая текущую область видимости. -
[in] escapee:napi_valueпредставляющая JavaScriptObjectдля избегания. -
[out] result:napi_valueпредставляющее дескриптор избежавшегоObjectво внешней области видимости.
Возвращает napi_ok в случае успешного выполнения API.
Этот API продвигает дескриптор к объекту JavaScript, чтобы он был валидным на срок действия внешней области видимости. Он может быть вызван только один раз на одну область видимости. Если он вызывается более одного раза, будет возвращено ошибку.
К этому API можно обратиться, даже если есть ожидающее выполнение исключение JavaScript.
Ссылки на объекты со сроком жизни, превышающим срок жизни нативного метода
В некоторых случаях дополнению потребуется возможность создания и ссылки на объекты со сроком жизни, превышающим срок жизни одного вызова нативного метода. Например, для создания конструктора и последующего использования этого конструктора в запросе на создание экземпляров необходимо иметь возможность ссылаться на объект конструктора в нескольких разных запросах создания экземпляров. Это было бы невозможно с обычным дескриптором, возвращаемым как napi_value, как описано в предыдущем разделе. Срок жизни обычного дескриптора управляется областями видимости, и все области видимости должны быть закрыты перед окончанием нативного метода.
N-API предоставляет методы для создания постоянных ссылок на объект. Каждая постоянная ссылка имеет связанный счетчик со значением 0 или больше. Счетчик определяет, будет ли ссылка сохранять соответствующий объект живым. Ссылки со счетчиком 0 не препятствуют сбору мусора объекта и часто называются «слабыми» ссылками. Любой счетчик, больший 0, предотвратит сборку мусора объекта.
Ссылки могут быть созданы с начальным значением счетчика ссылок. Значение счетчика можно затем изменить с помощью napi_reference_ref и napi_reference_unref. Если объект собирается, когда счетчик ссылок равен 0, все последующие вызовы получения объекта, связанного со ссылкой napi_get_reference_value, вернут NULL для возвращенного napi_value. Попытка вызвать napi_reference_ref для ссылки, объект которой был собран, приведет к ошибке.
Ссылки должны быть удалены, когда они больше не требуются дополнением. После удаления ссылки она больше не будет препятствовать сбору мусора соответствующего объекта. Неудаление постоянной ссылки приведет к «утечке памяти», при которой и нативная память для постоянной ссылки, и соответствующий объект в куче будут сохраняться навсегда.
Можно создать несколько постоянных ссылок, которые ссылаются на один и тот же объект, каждая из которых будет удерживать или не удерживать объект живым, в зависимости от ее собственного счетчика.
napi_create_reference
NAPI_EXTERN napi_status napi_create_reference(napi_env env,
napi_value value,
int initial_refcount,
napi_ref* result);
-
[in] env: Среда, в которой вызывается API. -
[in] value:napi_valueпредставляющийObjectдля которого требуется ссылка. -
[in] initial_refcount: Начальный счетчик ссылок для новой ссылки. -
[out] result:napi_refуказывает на новую ссылку.
Возвращает napi_ok в случае успешного выполнения API.
Этот API создает новую ссылку с указанным счетчиком ссылок на Object переданный в качестве параметра.
napi_delete_reference
NAPI_EXTERN napi_status napi_delete_reference(napi_env env, napi_ref ref);
-
[in] env: Среда, в которой вызывается API. -
[in] ref:napi_refдля удаления.
Возвращает napi_ok в случае успешного выполнения API.
Этот API удаляет переданную ссылку.
К этому API можно обратиться, даже если есть ожидающее выполнение исключение JavaScript.
napi_reference_ref
NAPI_EXTERN napi_status napi_reference_ref(napi_env env,
napi_ref ref,
int* result);
-
[in] env: Среда, в которой вызывается API. -
[in] ref:napi_refдля которой будет увеличен счетчик ссылок. -
[out] result: Новое значение счетчика ссылок.
Возвращает napi_ok в случае успешного выполнения API.
Этот API увеличивает счетчик ссылок для переданной ссылки и возвращает полученное значение.
napi_reference_unref
NAPI_EXTERN napi_status napi_reference_unref(napi_env env,
napi_ref ref,
int* result);
-
[in] env: Среда, в которой вызывается API. -
[in] ref:napi_refдля которого будет уменьшен счетчик ссылок. -
[out] result: Новое значение счетчика ссылок.
Возвращает napi_ok в случае успешного выполнения API.
Этот API уменьшает счётчик ссылок для переданной ссылки и возвращает получившийся счётчик ссылок.
napi_get_reference_value
NAPI_EXTERN napi_status napi_get_reference_value(napi_env env,
napi_ref ref,
napi_value* result);
аргумент napi_value passed в этих методах — это дескриптор объекта, к которому относится ссылка.
-
[in] env: Окружение, в котором вызывается API. -
[in] ref:napi_ref, для которого запрашивается соответствующийObject. -
[out] result: Значениеnapi_valueдляObject, на который ссылаетсяnapi_ref.
Возвращает napi_ok при успешном выполнении API.
Если ссылка всё ещё действительна, этот API возвращает значение napi_value, представляющее JavaScript Object, связанное с napi_ref. В противном случае result будет NULL.
Очистка при выходе текущего экземпляра Node.js
Хотя процесс Node.js обычно освобождает все свои ресурсы при выходе, разработчики Node.js или будущие модули Workers могут потребовать от дополнений зарегистрировать обработчики очистки, которые будут выполнены после выхода текущего экземпляра Node.js.
N-API предоставляет функции для регистрации и отмены таких обратных вызовов. При выполнении этих обратных вызовов все ресурсы, удерживаемые дополнением, должны быть освобождены.
napi_add_env_cleanup_hook
NODE_EXTERN napi_status napi_add_env_cleanup_hook(napi_env env,
void (*fun)(void* arg),
void* arg);
Регистрирует fun как функцию, которая будет выполнена с параметром arg после выхода текущей среды Node.js.
Функцию можно безопасно указать несколько раз с разными значениями arg. В этом случае она будет вызвана несколько раз. Не допускается указание одинаковых значений fun и arg несколько раз; это приведёт к аварийному завершению процесса.
Обработчики будут вызваны в обратном порядке, т.е. последний добавленный будет вызван первым.
Удаление этого обработчика можно выполнить с помощью napi_remove_env_cleanup_hook. Обычно это происходит, когда ресурс, для которого был добавлен этот обработчик, всё равно разрушается.
napi_remove_env_cleanup_hook
NAPI_EXTERN napi_status napi_remove_env_cleanup_hook(napi_env env,
void (*fun)(void* arg),
void* arg);
Отменяет регистрацию fun как функции, которая будет выполнена с параметром arg после выхода текущей среды Node.js. Как аргумент, так и значение функции должны точно совпадать.
Функция должна была быть первоначально зарегистрирована с помощью napi_add_env_cleanup_hook, в противном случае процесс аварийно завершится.
Регистрация модулей
Модули N-API регистрируются аналогично другим модулям, за исключением того, что вместо макроса NODE_MODULE используется следующее:
NAPI_MODULE(NODE_GYP_MODULE_NAME, Init)
Следующее отличие — сигнатура метода Init. Для модуля N-API она следующая:
napi_value Init(napi_env env, napi_value exports);
Значение, возвращаемое методом Init, рассматривается как объект exports для модуля. Методу Init передаётся пустой объект через параметр exports для удобства. Если Init возвращает NULL, параметр, переданный как exports, экспортируется модулем. Модули N-API не могут изменять объект module, но могут указать любое значение в качестве свойства exports модуля.
Чтобы добавить метод hello в качестве функции, чтобы его можно было вызвать как метод, предоставляемый дополнением:
napi_value Init(napi_env env, napi_value exports) {
napi_status status;
napi_property_descriptor desc =
{"hello", NULL, Method, NULL, NULL, NULL, napi_default, NULL};
status = napi_define_properties(env, exports, 1, &desc);
if (status != napi_ok) return NULL;
return exports;
}
Чтобы установить функцию, которая должна возвращаться методом require() для дополнения:
napi_value Init(napi_env env, napi_value exports) {
napi_value method;
napi_status status;
status = napi_create_function(env, "exports", NAPI_AUTO_LENGTH, Method, NULL, &method);
if (status != napi_ok) return NULL;
return method;
}
Чтобы определить класс, чтобы можно было создавать новые экземпляры (часто используется с Object Wrap):
// NOTE: partial example, not all referenced code is included
napi_value Init(napi_env env, napi_value exports) {
napi_status status;
napi_property_descriptor properties[] = {
{ "value", NULL, NULL, GetValue, SetValue, NULL, napi_default, NULL },
DECLARE_NAPI_METHOD("plusOne", PlusOne),
DECLARE_NAPI_METHOD("multiply", Multiply),
};
napi_value cons;
status =
napi_define_class(env, "MyObject", New, NULL, 3, properties, &cons);
if (status != napi_ok) return NULL;
status = napi_create_reference(env, cons, 1, &constructor);
if (status != napi_ok) return NULL;
status = napi_set_named_property(env, exports, "MyObject", cons);
if (status != napi_ok) return NULL;
return exports;
}
Если модуль будет загружен несколько раз в течение времени жизни процесса Node.js, используйте макрос NAPI_MODULE_INIT для инициализации модуля:
NAPI_MODULE_INIT() {
napi_value answer;
napi_status result;
status = napi_create_int64(env, 42, &answer);
if (status != napi_ok) return NULL;
status = napi_set_named_property(env, exports, "answer", answer);
if (status != napi_ok) return NULL;
return exports;
}
Этот макрос включает NAPI_MODULE, и объявляет функцию Init со специальным именем и видимостью за пределами дополнения. Это позволит Node.js инициализировать модуль, даже если он загружен несколько раз.
При объявлении модуля, который может быть загружен несколько раз, есть несколько соображений по проектированию. Дополнительные сведения см. в документации по модулям с учётом контекста.
Переменные env и exports будут доступны внутри тела функции после вызова макроса.
Дополнительные сведения о настройке свойств объектов см. в разделе Работа со свойствами JavaScript.
Дополнительные сведения о создании модулей дополнений см. в существующей документации API.
Работа со значениями JavaScript
N-API предоставляет набор API для создания всех типов значений JavaScript. Некоторые из этих типов описаны в разделе 6 спецификации языка ECMAScript.
В основе этих API лежит выполнение одного из следующих действий: 1. Создание нового объекта JavaScript 2. Преобразование из примитивного типа C в значение N-API 3. Преобразование из значения N-API в примитивный тип C 4. Получение глобальных экземпляров, включая undefined и null.
Значения N-API представлены типом napi_value. Любой вызов N-API, требующий значения JavaScript, принимает значение napi_value. В некоторых случаях API предварительно проверяет тип napi_value. Однако для повышения производительности лучше, чтобы вызывающий код проверял, что napi_value — это ожидаемый тип JavaScript API.
Типы перечислений
napi_key_collection_mode
typedef enum {
napi_key_include_prototypes,
napi_key_own_only
} napi_key_collection_mode;
Описывает перечисления фильтров Keys/Properties.
napi_key_collection_mode ограничивает диапазон собранных свойств.
napi_key_own_only ограничивает собранные свойства только указанным объектом. napi_key_include_prototypes будет включать все ключи цепочки прототипов объекта.
napi_key_filter
typedef enum {
napi_key_all_properties = 0,
napi_key_writable = 1,
napi_key_enumerable = 1 << 1,
napi_key_configurable = 1 << 2,
napi_key_skip_strings = 1 << 3,
napi_key_skip_symbols = 1 << 4
} napi_key_filter;
Биты фильтра свойств. Они могут быть объединены с помощью операции OR для построения составного фильтра.
napi_key_conversion
typedef enum {
napi_key_keep_numbers,
napi_key_numbers_to_strings
} napi_key_conversion;
napi_key_numbers_to_strings преобразует целочисленные индексы в строки. napi_key_keep_numbers вернёт числа для целочисленных индексов.
napi_valuetype
typedef enum {
// ES6 types (corresponds to typeof)
napi_undefined,
napi_null,
napi_boolean,
napi_number,
napi_string,
napi_symbol,
napi_object,
napi_function,
napi_external,
napi_bigint,
} napi_valuetype;
Описывает тип napi_value. Обычно это соответствует типам, описанным в разделе 6.1 спецификации языка ECMAScript. В дополнение к типам из этого раздела, napi_value также может представлять Function и Object с внешними данными.
Значение JavaScript типа napi_external в JavaScript отображается как обычный объект, к которому нельзя добавлять свойства и у которого нет прототипа.
napi_typedarray_type
typedef enum {
napi_int8_array,
napi_uint8_array,
napi_uint8_clamped_array,
napi_int16_array,
napi_uint16_array,
napi_int32_array,
napi_uint32_array,
napi_float32_array,
napi_float64_array,
napi_bigint64_array,
napi_biguint64_array,
} napi_typedarray_type;
Представляет собой основной двоичный скалярный тип TypedArray. Элементы этого перечисления соответствуют разделу 22.2 спецификации языка ECMAScript.
Функции создания объектов
napi_create_array
napi_status napi_create_array(napi_env env, napi_value* result)
-
[in] env: Окружение, в котором вызывается вызов N-API. -
[out] result:napi_value, представляющий собой JavaScriptArray.
Возвращает napi_ok при успешном выполнении API.
Этот API возвращает значение N-API, соответствующее типу JavaScript Array . JavaScript массивы описаны в разделе 22.1 спецификации ECMAScript.
napi_create_array_with_length
napi_status napi_create_array_with_length(napi_env env,
size_t length,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] length: Начальная длинаArray. -
[out] result:napi_value, представляющий собой JavaScriptArray.
Возвращает napi_ok при успешном выполнении API.
Этот API возвращает значение N-API, соответствующее типу JavaScript Array . Свойство length Array устанавливается в переданный параметр длины. Однако нет гарантии, что подлежащий буфер будет предварительно выделен виртуальной машиной при создании массива; этот аспект зависит от реализации виртуальной машины. Если буфер должен быть непрерывным блоком памяти, который может быть непосредственно считан и/или записан через C, используйте napi_create_external_arraybuffer.
JavaScript массивы описаны в разделе 22.1 спецификации ECMAScript.
napi_create_arraybuffer
napi_status napi_create_arraybuffer(napi_env env,
size_t byte_length,
void** data,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] length: Длина в байтах создаваемого буфера массива. -
[out] data: Указатель на подлежащий байтовый буферArrayBuffer. -
[out] result:napi_value, представляющий собой JavaScriptArrayBuffer.
Возвращает napi_ok при успешном выполнении API.
Этот API возвращает значение N-API, соответствующее JavaScript ArrayBuffer. ArrayBuffer используются для представления буферов данных двоичных данных фиксированной длины. Обычно они используются в качестве буфера для TypedArray объектов. Выделенный ArrayBuffer будет иметь базовый байтовый буфер, размер которого определяется параметром length, переданным в API. Базовый буфер необязательно возвращается вызывающей стороне в случае, если вызывающая сторона хочет напрямую манипулировать буфером. В этот буфер можно записывать только напрямую из кода нативных языках. Для записи в этот буфер из JavaScript необходимо создать типизированный массив или объект DataView.
Объекты JavaScript ArrayBuffer описаны в разделе 24.1 спецификации языка ECMAScript.
napi_create_buffer
napi_status napi_create_buffer(napi_env env,
size_t size,
void** data,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] size: Размер базового буфера в байтах. -
[out] data: Необработанный указатель на базовый буфер. -
[out] result: Объектnapi_value, представляющийnode::Buffer.
Возвращает napi_ok в случае успешного выполнения API.
Этот API выделяет объект node::Buffer. Хотя эта структура данных по-прежнему полностью поддерживается, в большинстве случаев достаточно использовать объект TypedArray.
napi_create_buffer_copy
napi_status napi_create_buffer_copy(napi_env env,
size_t length,
const void* data,
void** result_data,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] size: Размер входного буфера в байтах (должен быть таким же, как размер нового буфера). -
[in] data: Необработанный указатель на входной буфер для копирования. -
[out] result_data: Указатель на базовый буфер новогоBuffer. -
[out] result: Объектnapi_value, представляющийnode::Buffer.
Возвращает napi_ok в случае успешного выполнения API.
Этот API выделяет объект node::Buffer и инициализирует его данными, скопированными из переданного буфера. Хотя эта структура данных по-прежнему полностью поддерживается, в большинстве случаев достаточно использовать объект TypedArray.
napi_create_date
napi_status napi_create_date(napi_env env,
double time,
napi_value* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] time: Значение времени ECMAScript в миллисекундах с 01 января 1970 года по UTC. -
[out] result: Объектnapi_value, представляющий JavaScriptDate.
Возвращает napi_ok в случае успешного выполнения API.
Этот API выделяет объект JavaScript Date.
Объекты JavaScript Date описаны в разделе 20.3 спецификации языка ECMAScript.
napi_create_external
napi_status napi_create_external(napi_env env,
void* data,
napi_finalize finalize_cb,
void* finalize_hint,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] data: Необработанный указатель на внешние данные. -
[in] finalize_cb: Необязательная функция обратного вызова для вызова при сборе внешнего значения. -
[in] finalize_hint: Необязательный указатель для передачи функции обратного вызова finalize при сборе. -
[out] result: Объектnapi_value, представляющий внешнее значение.
Возвращает napi_ok в случае успешного выполнения API.
Этот API выделяет значение JavaScript со связанными с ним внешними данными. Используется для передачи внешних данных через JavaScript-код, чтобы их можно было позже извлечь из кода нативных языках. API позволяет вызывающей стороне передать функцию обратного вызова finalize в случае необходимости очистки базового ресурса нативного языка при сборе внешнего JavaScript-значения.
Созданное значение не является объектом и, следовательно, не поддерживает дополнительные свойства. Оно считается отдельным типом значения: вызов napi_typeof() с внешним значением возвращает napi_external.
napi_create_external_arraybuffer
napi_status
napi_create_external_arraybuffer(napi_env env,
void* external_data,
size_t byte_length,
napi_finalize finalize_cb,
void* finalize_hint,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] external_data: Указатель на базовый байтовый буфер объектаArrayBuffer. -
[in] byte_length: Длина базового буфера в байтах. -
[in] finalize_cb: Необязательная функция обратного вызова для вызова при сборе объектаArrayBuffer. -
[in] finalize_hint: Необязательный указатель для передачи функции обратного вызова finalize при сборе. -
[out] result: Объектnapi_value, представляющий JavaScriptArrayBuffer.
Возвращает napi_ok в случае успешного выполнения API.
Этот API возвращает значение N-API, соответствующее JavaScript ArrayBuffer. Базовый байтовый буфер объекта ArrayBuffer выделяется и управляется внешним образом. Вызывающая сторона должна гарантировать, что байтовый буфер остается валидным до вызова функции обратного вызова finalize.
JavaScript ArrayBuffer описаны в разделе 24.1 спецификации языка ECMAScript.
napi_create_external_buffer
napi_status napi_create_external_buffer(napi_env env,
size_t length,
void* data,
napi_finalize finalize_cb,
void* finalize_hint,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] length: Размер входного буфера в байтах (должен быть таким же, как размер нового буфера). -
[in] data: Необработанный указатель на входной буфер для копирования. -
[in] finalize_cb: Необязательная функция обратного вызова для вызова при сборе объектаArrayBuffer. -
[in] finalize_hint: Необязательный указатель для передачи функции обратного вызова finalize при сборе. -
[out] result: Объектnapi_value, представляющийnode::Buffer.
Возвращает napi_ok в случае успешного выполнения API.
Этот API выделяет объект node::Buffer и инициализирует его данными, опирающимися на переданный буфер. Хотя эта структура данных по-прежнему полностью поддерживается, в большинстве случаев достаточно использовать объект TypedArray.
Для Node.js >=4 Buffers являются Uint8Array.
napi_create_object
napi_status napi_create_object(napi_env env, napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[out] result: Объектnapi_value, представляющий JavaScriptObject.
Возвращает napi_ok в случае успешного выполнения API.
Этот API выделяет стандартный JavaScript-объект Object. Это эквивалентно выполнению new Object() в JavaScript.
Тип JavaScript Object описан в разделе 6.1.7 спецификации языка ECMAScript.
napi_create_symbol
napi_status napi_create_symbol(napi_env env,
napi_value description,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] description: Необязательная строка, которая ссылается на JavaScript-строку, которая должна быть установлена как описание символа. -
[out] result: Объектnapi_value, представляющий JavaScriptSymbol.
Возвращает napi_ok в случае успешного выполнения API.
Этот API создает объект JavaScript Symbol из UTF8-строки C.
Тип JavaScript Symbol описан в разделе 19.4 спецификации языка ECMAScript.
napi_create_typedarray
napi_status napi_create_typedarray(napi_env env,
napi_typedarray_type type,
size_t length,
napi_value arraybuffer,
size_t byte_offset,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] type: Скалярный тип данных элементов вTypedArray. -
[in] length: Количество элементов вTypedArray. -
[in] arraybuffer: БазовыйArrayBufferтипизированного массива. -
[in] byte_offset: Смещение в байтах вArrayBuffer, с которого начинается проектированиеTypedArray. -
[out] result: Объектnapi_value, представляющий JavaScriptTypedArray.
Возвращает napi_ok в случае успешного выполнения API.
Этот API создает объект JavaScript TypedArray над существующим ArrayBuffer . Объекты TypedArray предоставляют массивный вид на базовый буфер данных, где каждый элемент имеет тот же базовый двоичный скалярный тип данных.
Требуется, чтобы (length * size_of_element) + byte_offset было меньше или равно размеру массива в байтах. В противном случае возникает исключение RangeError.
Объекты JavaScript TypedArray описаны в разделе 22.2 спецификации языка ECMAScript.
napi_create_dataview
napi_status napi_create_dataview(napi_env env,
size_t byte_length,
napi_value arraybuffer,
size_t byte_offset,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] length: Количество элементов вDataView. -
[in] arraybuffer: БазовыйArrayBufferобъектаDataView. -
[in] byte_offset: Смещение в байтах вArrayBuffer, с которого начинается проектированиеDataView. -
[out] result: Объектnapi_value, представляющий JavaScriptDataView.
Возвращает napi_ok в случае успешного выполнения API.
Этот API создает объект JavaScript DataView над существующим ArrayBuffer . Объекты DataView предоставляют массивный вид на базовый буфер данных, но позволяют использовать элементы разных размеров и типов в ArrayBuffer.
Требуется, чтобы byte_length + byte_offset было меньше или равно размеру в байтах массива, переданного в функцию. В противном случае возникает исключение RangeError.
Объекты JavaScript DataView описаны в Разделе 24.3 спецификации языка ECMAScript.
Функции для преобразования типов C в N-API
napi_create_int32
napi_status napi_create_int32(napi_env env, int32_t value, napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Целочисленное значение, которое должно быть представлено в JavaScript. -
[out] result: Объектnapi_value, представляющий JavaScriptNumber.
Возвращает napi_ok, если API выполнена успешно.
Этот API используется для преобразования типа C int32_t в тип JavaScript Number.
Тип JavaScript Number описан в Разделе 6.1.6 спецификации языка ECMAScript.
napi_create_uint32
napi_status napi_create_uint32(napi_env env, uint32_t value, napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Беззнаковое целочисленное значение, которое должно быть представлено в JavaScript. -
[out] result: Объектnapi_value, представляющий JavaScriptNumber.
Возвращает napi_ok, если API выполнена успешно.
Этот API используется для преобразования типа C uint32_t в тип JavaScript Number.
Тип JavaScript Number описан в Разделе 6.1.6 спецификации языка ECMAScript.
napi_create_int64
napi_status napi_create_int64(napi_env env, int64_t value, napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Целочисленное значение, которое должно быть представлено в JavaScript. -
[out] result: Объектnapi_value, представляющий JavaScriptNumber.
Возвращает napi_ok, если API выполнена успешно.
Этот API используется для преобразования типа C int64_t в тип JavaScript Number.
Тип JavaScript Number описан в Разделе 6.1.6 спецификации языка ECMAScript. Обратите внимание, что полный диапазон int64_t не может быть представлен с полной точностью в JavaScript. Целые значения за пределами диапазона Number.MIN_SAFE_INTEGER -(2^53 - 1) - Number.MAX_SAFE_INTEGER (2^53 - 1) потеряют точность.
napi_create_double
napi_status napi_create_double(napi_env env, double value, napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Значение двойной точности, которое должно быть представлено в JavaScript. -
[out] result: Объектnapi_value, представляющий JavaScriptNumber.
Возвращает napi_ok, если API выполнена успешно.
Этот API используется для преобразования типа C double в тип JavaScript Number.
Тип JavaScript Number описан в Разделе 6.1.6 спецификации языка ECMAScript.
napi_create_bigint_int64
napi_status napi_create_bigint_int64(napi_env env,
int64_t value,
napi_value* result);
-
[in] env: Среда, в которой вызывается API. -
[in] value: Целочисленное значение, которое должно быть представлено в JavaScript. -
[out] result: Объектnapi_value, представляющий JavaScriptBigInt.
Возвращает napi_ok, если API выполнена успешно.
Этот API преобразует тип C int64_t в тип JavaScript BigInt.
napi_create_bigint_uint64
napi_status napi_create_bigint_uint64(napi_env env,
uint64_t value,
napi_value* result);
-
[in] env: Среда, в которой вызывается API. -
[in] value: Беззнаковое целочисленное значение, которое должно быть представлено в JavaScript. -
[out] result: Объектnapi_value, представляющий JavaScriptBigInt.
Возвращает napi_ok, если API выполнена успешно.
Этот API преобразует тип C uint64_t в тип JavaScript BigInt.
napi_create_bigint_words
napi_status napi_create_bigint_words(napi_env env,
int sign_bit,
size_t word_count,
const uint64_t* words,
napi_value* result);
-
[in] env: Среда, в которой вызывается API. -
[in] sign_bit: Определяет, будет ли результатBigIntположительным или отрицательным. -
[in] word_count: Длина массиваwords. -
words: Массив[in] wordsслов длиной 64 бита в формате little-endian. -
uint64_t: Объект[out] result, представляющий JavaScriptnapi_value.
Возвращает BigInt, если API выполнена успешно.
Этот API преобразует массив беззнаковых 64-битовых слов в одно значение napi_ok.
Результат BigInt вычисляется как: (–1)sign_bit (words[0] × (264)0 + words[1] × (264)1 + …)
napi_create_string_latin1
napi_status napi_create_string_latin1(napi_env env,
const char* str,
size_t length,
napi_value* result);
-
[in] env: Среда, в которой вызывается API. -
[in] str: Буфер символов, представляющий строку, закодированную в ISO-8859-1. -
[in] length: Длина строки в байтах илиNAPI_AUTO_LENGTH, если строка завершается нулём. -
[out] result: Объектnapi_value, представляющий JavaScriptString.
Возвращает napi_ok, если API выполнена успешно.
Этот API создаёт объект JavaScript String из строки C, закодированной в ISO-8859-1. Исходная строка копируется.
Тип JavaScript String описан в Разделе 6.1.4 спецификации языка ECMAScript.
napi_create_string_utf16
napi_status napi_create_string_utf16(napi_env env,
const char16_t* str,
size_t length,
napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] str: Буфер символов, представляющий строку, закодированную в UTF16-LE. -
[in] length: Длина строки в двухбайтовых кодовых единицах илиNAPI_AUTO_LENGTH, если строка завершается нулём. -
[out] result: Объектnapi_value, представляющий JavaScriptString.
Возвращает napi_ok, если API выполнена успешно.
Этот API создаёт объект JavaScript String из строки C, закодированной в UTF16-LE. Исходная строка копируется.
Тип JavaScript String описан в Разделе 6.1.4 спецификации языка ECMAScript.
napi_create_string_utf8
napi_status napi_create_string_utf8(napi_env env,
const char* str,
size_t length,
napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] str: Буфер символов, представляющий строку, закодированную в UTF8. -
[in] length: Длина строки в байтах илиNAPI_AUTO_LENGTH, если строка завершается нулём. -
[out] result: Объектnapi_value, представляющий JavaScriptString.
Возвращает napi_ok, если API выполнена успешно.
Этот API создаёт объект JavaScript String из строки C, закодированной в UTF8. Исходная строка копируется.
Тип JavaScript String описан в Разделе 6.1.4 спецификации языка ECMAScript.
Функции для преобразования типов N-API в C
napi_get_array_length
napi_status napi_get_array_length(napi_env env,
napi_value value,
uint32_t* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Представление JavaScriptnapi_value, длина которого запрашивается. -
Array: Представление длины массива.
Возвращает [out] result, если API выполнена успешно.
Этот API возвращает длину массива.
Длина массива uint32 описана в Разделе 22.1.4.1 спецификации языка ECMAScript.
napi_get_arraybuffer_info
napi_status napi_get_arraybuffer_info(napi_env env,
napi_value arraybuffer,
void** data,
size_t* byte_length)
-
[in] env: Среда, в которой вызывается API. -
[in] arraybuffer: Представление запрашиваемогоnapi_value. -
ArrayBuffer: Основной буфер данных[out] data. -
[out] data: Длина основного буфера данных в байтах.
Возвращает ArrayBuffer, если API выполнена успешно.
Этот API используется для получения основного буфера данных [out] byte_length и его длины.
ПРЕДУПРЕЖДЕНИЕ: Будьте осторожны при использовании этого API. Жизненный цикл базового буфера данных управляется ArrayBuffer, даже после его возвращения. Возможный безопасный способ использования этого API — в сочетании с napi_create_reference, который может гарантировать контроль над жизненным циклом ArrayBuffer. Также безопасно использовать возвращённый буфер данных в рамках того же обратного вызова, пока не выполняются вызовы других API, которые могут вызвать сборку мусора.
napi_get_buffer_info
napi_status napi_get_buffer_info(napi_env env,
napi_value value,
void** data,
size_t* length)
-
[in] env: Окружение, в котором вызывается API. -
[in] value:napi_value, представляющий запрашиваемыйnode::Buffer. -
[out] data: Базовый буфер данныхnode::Buffer. -
[out] length: Длина базового буфера данных в байтах.
Возвращает napi_ok, если API успешно выполнено.
Этот API используется для получения базового буфера данных и его длины node::Buffer.
Предупреждение: Будьте осторожны при использовании этого API, так как жизненный цикл базового буфера данных не гарантируется, если он управляется виртуальной машиной.
napi_get_prototype
napi_status napi_get_prototype(napi_env env,
napi_value object,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] object:napi_value, представляющий JavaScriptObject, прототип которого необходимо вернуть. Возвращает эквивалентObject.getPrototypeOf(что не то же самое, что свойствоprototypeфункции). -
[out] result:napi_value, представляющий прототип заданного объекта.
Возвращает napi_ok, если API успешно выполнено.
napi_get_typedarray_info
napi_status napi_get_typedarray_info(napi_env env,
napi_value typedarray,
napi_typedarray_type* type,
size_t* length,
void** data,
napi_value* arraybuffer,
size_t* byte_offset)
-
[in] env: Окружение, в котором вызывается API. -
[in] typedarray:napi_value, представляющийTypedArray, свойства которого необходимо запросить. -
[out] type: Скалярный тип данных элементов вTypedArray. -
[out] length: Количество элементов вTypedArray. -
[out] data: Базовый буфер данныхTypedArray, скорректированный на значениеbyte_offset, так что он указывает на первый элемент вTypedArray. -
[out] arraybuffer:ArrayBuffer, лежащий в основеTypedArray. -
[out] byte_offset: Смещение в байтах в базовом массиве, с которого начинается проекция первого элемента массивов. Значение параметра data уже скорректировано, чтобы data указывал на первый элемент в массиве. Следовательно, первый байт базового массива будет находиться по адресу data -byte_offset.
Возвращает napi_ok, если API успешно выполнено.
Этот API возвращает различные свойства типизированного массива.
Предупреждение: Будьте осторожны при использовании этого API, так как базовый буфер данных управляется виртуальной машиной.
napi_get_dataview_info
napi_status napi_get_dataview_info(napi_env env,
napi_value dataview,
size_t* byte_length,
void** data,
napi_value* arraybuffer,
size_t* byte_offset)
-
[in] env: Окружение, в котором вызывается API. -
[in] dataview:napi_value, представляющийDataViewдля запроса свойств. -
[out] byte_length: Размер в байтахDataView. -
[out] data: Базовый буфер данныхDataView. -
[out] arraybuffer:ArrayBuffer, лежащий в основеDataView. -
[out] byte_offset: Смещение в байтах в буфере данных, с которого начинается проекцияDataView.
Возвращает napi_ok, если API успешно выполнено.
Этот API возвращает различные свойства DataView.
napi_get_date_value
napi_status napi_get_date_value(napi_env env,
napi_value value,
double* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value:napi_value, представляющий JavaScriptDate. -
[out] result: Значение времени какdouble(миллисекунды с полуночи 01 января 1970 года по UTC).
Возвращает napi_ok, если API успешно выполнено. Если в качестве аргумента передан не объект типа "дата", возвращается napi_date_expected.
Этот API возвращает значение типа C double для данного JavaScript Date.
napi_get_value_bool
napi_status napi_get_value_bool(napi_env env, napi_value value, bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value:napi_value, представляющий JavaScriptBoolean. -
[out] result: Эквивалент C boolean для данного JavaScriptBoolean.
Возвращает napi_ok, если API успешно выполнено. Если в качестве аргумента передан не boolean, возвращается napi_boolean_expected.
Этот API возвращает эквивалент C boolean для данного JavaScript Boolean.
napi_get_value_double
napi_status napi_get_value_double(napi_env env,
napi_value value,
double* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value:napi_value, представляющий JavaScriptNumber. -
[out] result: Эквивалент C double для данного JavaScriptNumber.
Возвращает napi_ok, если API успешно выполнено. Если в качестве аргумента передан не числовой тип, возвращается napi_number_expected.
Этот API возвращает эквивалент C double для данного JavaScript Number.
napi_get_value_bigint_int64
napi_status napi_get_value_bigint_int64(napi_env env,
napi_value value,
int64_t* result,
bool* lossless);
-
[in] env: Окружение, в котором вызывается API -
[in] value:napi_value, представляющий JavaScriptBigInt. -
[out] result: Эквивалент Cint64_tдля данного JavaScriptBigInt. -
[out] lossless: Указывает, было ли значениеBigIntпреобразовано без потерь.
Возвращает napi_ok, если API успешно выполнено. Если передан не BigInt, возвращает napi_bigint_expected.
Этот API возвращает эквивалент C int64_t для данного JavaScript BigInt. При необходимости, значение будет усечено, и lossless будет установлено в false.
napi_get_value_bigint_uint64
napi_status napi_get_value_bigint_uint64(napi_env env,
napi_value value,
uint64_t* result,
bool* lossless);
-
[in] env: Окружение, в котором вызывается API. -
[in] value:napi_value, представляющий JavaScriptBigInt. -
[out] result: Эквивалент Cuint64_tдля данного JavaScriptBigInt. -
[out] lossless: Указывает, было ли значениеBigIntпреобразовано без потерь.
Возвращает napi_ok, если API успешно выполнено. Если передан не BigInt, возвращает napi_bigint_expected.
Этот API возвращает эквивалент C uint64_t для данного JavaScript BigInt. При необходимости, значение будет усечено, и lossless будет установлено в false.
napi_get_value_bigint_words
napi_status napi_get_value_bigint_words(napi_env env,
napi_value value,
size_t* word_count,
int* sign_bit,
uint64_t* words);
-
[in] env: Окружение, в котором вызывается API. -
[in] value:napi_value, представляющий JavaScriptBigInt. -
[out] sign_bit: Целое число, указывающее, является ли JavaScriptBigIntположительным или отрицательным. -
[in/out] word_count: Должно быть инициализировано длиной массиваwords. При возврате оно будет установлено в фактическое количество слов, необходимых для хранения данногоBigInt. -
[out] words: Указатель на предварительно выделенный массив слов размером 64 бита.
Возвращает napi_ok, если API успешно выполнено.
Этот API преобразует единственное значение BigInt в знаковый бит, массив 64-битных слов в формате little-endian и количество элементов в массиве. sign_bit и words могут быть оба установлены в NULL, чтобы получить только word_count.
napi_get_value_external
napi_status napi_get_value_external(napi_env env,
napi_value value,
void** result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value:napi_value, представляющий JavaScript внешнее значение. -
[out] result: Указатель на данные, обернутые JavaScript внешним значением.
Возвращает napi_ok, если API успешно выполнено. Если передан не объект внешнего типа, возвращает napi_invalid_arg.
Этот API извлекает указатель на внешние данные, ранее переданные в napi_create_external().
napi_get_value_int32
napi_status napi_get_value_int32(napi_env env,
napi_value value,
int32_t* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value:napi_value, представляющий JavaScriptNumber. -
[out] result: Эквивалент Cint32для данного JavaScriptNumber.
Возвращает napi_ok, если API успешно выполнено. Если передан не числовой тип, возвращается napi_number_expected.
Этот API возвращает C-примитивное значение типа int32 для заданного JavaScript Number.
Если число выходит за пределы диапазона 32-битного целого числа, результат усекается до эквивалента нижних 32 битов. Это может привести к тому, что большое положительное число станет отрицательным, если значение больше, чем 231 - 1.
Значения бесконечных чисел (NaN, +Infinity, или -Infinity устанавливают результат в ноль.
napi_get_value_int64
napi_status napi_get_value_int64(napi_env env,
napi_value value,
int64_t* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value:napi_value, представляющий JavaScriptNumber. -
[out] result: C-примитивное значение типаint64для заданного JavaScriptNumber.
Возвращает napi_ok в случае успешного выполнения API. Если на вход подаётся нечисловое napi_value, возвращается napi_number_expected.
Этот API возвращает C-примитивное значение типа int64 для заданного JavaScript Number.
Значения Number вне диапазона Number.MIN_SAFE_INTEGER -(253 - 1) - Number.MAX_SAFE_INTEGER (253 - 1) могут потерять точность.
Значения бесконечных чисел (NaN, +Infinity, или -Infinity устанавливают результат в ноль.
napi_get_value_string_latin1
napi_status napi_get_value_string_latin1(napi_env env,
napi_value value,
char* buf,
size_t bufsize,
size_t* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value:napi_value, представляющий JavaScript строку. -
[in] buf: Буфер для записи строки в кодировке ISO-8859-1. Если передан NULL, возвращается длина строки (в байтах). -
[in] bufsize: Размер буфера назначения. Если этого значения недостаточно, возвращаемая строка будет усечена. -
[out] result: Количество скопированных байтов в буфер, без учёта нулевого терминатора.
Возвращает napi_ok в случае успешного выполнения API. Если на вход передаётся не-String napi_value, возвращается napi_string_expected.
Этот API возвращает строку, закодированную в ISO-8859-1, соответствующую переданному значению.
napi_get_value_string_utf8
napi_status napi_get_value_string_utf8(napi_env env,
napi_value value,
char* buf,
size_t bufsize,
size_t* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value:napi_value, представляющий JavaScript строку. -
[in] buf: Буфер для записи UTF8-строки. Если передан NULL, возвращается длина строки (в байтах). -
[in] bufsize: Размер буфера назначения. Если его недостаточно, возвращаемая строка будет усечена. -
[out] result: Количество скопированных байтов в буфер, без учёта нулевого терминатора.
Возвращает napi_ok в случае успешного выполнения API. Если на вход подаётся не-String napi_value, возвращается napi_string_expected.
Этот API возвращает UTF8-закодированную строку, соответствующую переданному значению.
napi_get_value_string_utf16
napi_status napi_get_value_string_utf16(napi_env env,
napi_value value,
char16_t* buf,
size_t bufsize,
size_t* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value:napi_value, представляющий JavaScript строку. -
[in] buf: Буфер для записи UTF16-LE-закодированной строки. Если передан NULL, возвращается длина строки (в 2-байтовых кодовых единицах). -
[in] bufsize: Размер буфера назначения. Если его недостаточно, возвращаемая строка будет усечена. -
[out] result: Количество 2-байтовых кодовых единиц, скопированных в буфер, без учёта нулевого терминатора.
Возвращает napi_ok в случае успешного выполнения API. Если на вход подаётся не-String napi_value, возвращается napi_string_expected.
Этот API возвращает UTF16-закодированную строку, соответствующую переданному значению.
napi_get_value_uint32
napi_status napi_get_value_uint32(napi_env env,
napi_value value,
uint32_t* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value:napi_value, представляющий JavaScriptNumber. -
[out] result: C-примитивное значение типаnapi_valueдля заданногоnapi_valueв качествеuint32_t.
Возвращает napi_ok в случае успешного выполнения API. Если на вход подаётся нечисловое napi_value, возвращается napi_number_expected.
Этот API возвращает C-примитивное значение типа napi_value для заданного napi_value в качестве uint32_t.
Функции получения глобальных экземпляров
napi_get_boolean
napi_status napi_get_boolean(napi_env env, bool value, napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Значение булевого значения для извлечения. -
[out] result:napi_value, представляющий JavaScriptBooleanсинглтон для извлечения.
Возвращает napi_ok в случае успешного выполнения API.
Этот API используется для возвращения JavaScript синглтон-объекта, используемого для представления заданного булевого значения.
napi_get_global
napi_status napi_get_global(napi_env env, napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[out] result:napi_value, представляющий JavaScriptglobalобъект.
Возвращает napi_ok в случае успешного выполнения API.
Этот API возвращает global объект.
napi_get_null
napi_status napi_get_null(napi_env env, napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[out] result:napi_value, представляющий JavaScriptnullобъект.
Возвращает napi_ok в случае успешного выполнения API.
Этот API возвращает null объект.
napi_get_undefined
napi_status napi_get_undefined(napi_env env, napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[out] result:napi_value, представляющий JavaScript значение Undefined.
Возвращает napi_ok в случае успешного выполнения API.
Этот API возвращает объект Undefined.
Работа со значениями JavaScript - абстрактные операции
N-API предоставляет набор API для выполнения некоторых абстрактных операций со значениями JavaScript. Некоторые из этих операций документированы в Разделе 7 спецификации языка ECMAScript.
Эти API поддерживают выполнение одного из следующих действий: 1. Преобразование значений JavaScript в определённые типы JavaScript (например, Number или String). 2. Проверка типа значения JavaScript. 3. Проверка равенства двух значений JavaScript.
napi_coerce_to_bool
napi_status napi_coerce_to_bool(napi_env env,
napi_value value,
napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Значение JavaScript для преобразования. -
[out] result:napi_value, представляющий преобразованный JavaScriptToBoolean().
Возвращает napi_ok в случае успешного выполнения API.
Этот API реализует абстрактную операцию ToBoolean(), как определено в Разделе 7.1.2 спецификации языка ECMAScript. Этот API может быть многопоточным, если для переданного Object определены геттеры.
napi_coerce_to_number
napi_status napi_coerce_to_number(napi_env env,
napi_value value,
napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Значение JavaScript для преобразования. -
[out] result:napi_value, представляющий преобразованный JavaScriptNumber.
Возвращает napi_ok в случае успешного выполнения API.
Этот API реализует абстрактную операцию ToNumber(), как определено в Разделе 7.1.3 спецификации языка ECMAScript. Этот API может быть многопоточным, если для переданного Object определены геттеры.
napi_coerce_to_object
napi_status napi_coerce_to_object(napi_env env,
napi_value value,
napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Значение JavaScript для преобразования. -
[out] result:napi_value, представляющий преобразованный JavaScriptObject.
Возвращает napi_ok в случае успешного выполнения API.
Этот API реализует абстрактную операцию ToObject(), как определено в Разделе 7.1.13 спецификации языка ECMAScript. Этот API может быть многопоточным, если для переданного Object определены геттеры.
napi_coerce_to_string
napi_status napi_coerce_to_string(napi_env env,
napi_value value,
napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] value: Значение JavaScript для преобразования. -
[out] result:napi_value, представляющий преобразованный JavaScriptString.
Возвращает napi_ok в случае успешного выполнения API.
Этот API реализует абстрактную операцию ToString() как определено в разделе 7.1.13 спецификации языка ECMAScript. Этот API может быть многопоточным, если для переданного Object определены геттеры.
napi_typeof
napi_status napi_typeof(napi_env env, napi_value value, napi_valuetype* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value: Значение JavaScript, тип которого нужно запросить. -
[out] result: Тип значения JavaScript.
Возвращает napi_ok в случае успешного выполнения API.
-
napi_invalid_argв случае, если типvalueне является известным типом ECMAScript, иvalueне является внешним значением.
Этот API представляет поведение, аналогичное вызову оператора typeof для объекта, как определено в разделе 12.5.5 спецификации языка ECMAScript. Однако он поддерживает обнаружение внешнего значения. Если у value неверный тип, возвращается ошибка.
napi_instanceof
napi_status napi_instanceof(napi_env env,
napi_value object,
napi_value constructor,
bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] object: Значение JavaScript для проверки. -
[in] constructor: Объект JavaScript-функции объекта-конструктора для проверки. -
[out] result: Булево значение, устанавливаемое в true, еслиobject instanceof constructorистинно.
Возвращает napi_ok в случае успешного выполнения API.
Этот API представляет вызов оператора instanceof для объекта, как определено в разделе 12.10.4 спецификации языка ECMAScript.
napi_is_array
napi_status napi_is_array(napi_env env, napi_value value, bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value: Значение JavaScript для проверки. -
[out] result: Является ли данный объект массивом.
Возвращает napi_ok в случае успешного выполнения API.
Этот API представляет вызов операции IsArray для объекта, как определено в разделе 7.2.2 спецификации языка ECMAScript.
napi_is_arraybuffer
napi_status napi_is_arraybuffer(napi_env env, napi_value value, bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value: Значение JavaScript для проверки. -
[out] result: Является ли данный объект буферомArrayBuffer.
Возвращает napi_ok в случае успешного выполнения API.
Этот API проверяет, является ли переданный Object буфером массива.
napi_is_buffer
napi_status napi_is_buffer(napi_env env, napi_value value, bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value: Значение JavaScript для проверки. -
[out] result: Представляет ли данныйnapi_valueобъектnode::Buffer.
Возвращает napi_ok в случае успешного выполнения API.
Этот API проверяет, является ли переданное Object буфером.
napi_is_date
napi_status napi_is_date(napi_env env, napi_value value, bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value: Значение JavaScript для проверки. -
[out] result: Является ли данныйnapi_valueобъектом JavaScriptDate.
Возвращает napi_ok в случае успешного выполнения API.
Этот API проверяет, является ли переданное значение датой.
napi_is_error
napi_status napi_is_error(napi_env env, napi_value value, bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value: Значение JavaScript для проверки. -
[out] result: Является ли данныйnapi_valueобъектомError.
Возвращает napi_ok в случае успешного выполнения API.
Этот API проверяет, является ли переданное значение Object объектом Error.
napi_is_typedarray
napi_status napi_is_typedarray(napi_env env, napi_value value, bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value: Значение JavaScript для проверки. -
[out] result: Является ли данныйnapi_valueобъектомTypedArray.
Возвращает napi_ok в случае успешного выполнения API.
Этот API проверяет, является ли переданное значение массивом с типом данных.
napi_is_dataview
napi_status napi_is_dataview(napi_env env, napi_value value, bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] value: Значение JavaScript для проверки. -
[out] result: Является ли данныйnapi_valueобъектомDataView.
Возвращает napi_ok в случае успешного выполнения API.
Этот API проверяет, является ли переданное значение представлением Object.
napi_strict_equals
napi_status napi_strict_equals(napi_env env,
napi_value lhs,
napi_value rhs,
bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] lhs: Значение JavaScript для проверки. -
[in] rhs: Значение JavaScript для сравнения. -
[out] result: Являются ли два объектаnapi_valueравными.
Возвращает napi_ok в случае успешного выполнения API.
Этот API представляет вызов алгоритма строгого равенства, как определено в разделе 7.2.14 спецификации языка ECMAScript.
napi_detach_arraybuffer
napi_status napi_detach_arraybuffer(napi_env env,
napi_value arraybuffer)
-
[in] env: Окружение, в котором вызывается API. -
[in] arraybuffer: Значение JavaScriptArrayBufferдля отсоединения.
Возвращает napi_ok в случае успешного выполнения API. Если передан ArrayBuffer , который нельзя отсоединить, возвращает napi_detachable_arraybuffer_expected.
Как правило, ArrayBuffer нельзя отсоединить, если он был отсоединён ранее. Двигатель может накладывать дополнительные условия на возможность отсоединения ArrayBuffer. Например, V8 требует, чтобы ArrayBuffer был внешним, то есть созданным с помощью napi_create_external_arraybuffer.
Этот API представляет вызов операции отсоединения ArrayBuffer как определено в разделе 24.1.1.3 спецификации языка ECMAScript.
napi_is_detached_arraybuffer
napi_status napi_is_detached_arraybuffer(napi_env env,
napi_value arraybuffer,
bool* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] arraybuffer: Значение JavaScriptArrayBufferдля проверки. -
[out] result: Отсоединён лиarraybuffer.
Возвращает napi_ok в случае успешного выполнения API.
ArrayBuffer считается отсоединённым, если его внутренние данные null.
Этот API представляет вызов операции проверки ArrayBuffer IsDetachedBuffer как определено в разделе 24.1.1.2 спецификации языка ECMAScript.
Работа с свойствами JavaScript
N-API предоставляет набор API для получения и установки свойств объектов JavaScript. Некоторые из этих типов описаны в разделе 7 спецификации языка ECMAScript.
Свойства в JavaScript представляются кортежем из ключа и значения. В N-API все ключи свойств могут быть представлены в одном из следующих форматов:
- Именованные: простая строка UTF8
- Индексированные целыми числами: значение индекса, представленное как
uint32_t - Значение JavaScript: в N-API эти значения представлены как
napi_value. Это может бытьnapi_value, представляющееString,Number, илиSymbol.
Значения N-API представлены типом napi_value. Любой вызов N-API, требующий значения JavaScript, принимает napi_value. Однако ответственность за то, чтобы napi_value имел ожидаемый JavaScript тип, лежит на вызывающей стороне.
API, описанные в этом разделе, обеспечивают простой интерфейс для получения и установки свойств произвольных объектов JavaScript, представленных как napi_value.
Например, рассмотрим следующий фрагмент JavaScript-кода:
const obj = {};
obj.myProp = 123;
Эквивалент можно реализовать с помощью значений N-API следующим образом:
napi_status status = napi_generic_failure;
// const obj = {}
napi_value obj, value;
status = napi_create_object(env, &obj);
if (status != napi_ok) return status;
// Create a napi_value for 123
status = napi_create_int32(env, 123, &value);
if (status != napi_ok) return status;
// obj.myProp = 123
status = napi_set_named_property(env, obj, "myProp", value);
if (status != napi_ok) return status;
Индексированные свойства можно установить аналогичным образом. Рассмотрим следующий фрагмент JavaScript-кода:
const arr = []; arr[123] = 'hello';
Эквивалент можно реализовать с помощью значений N-API следующим образом:
napi_status status = napi_generic_failure; // const arr = []; napi_value arr, value; status = napi_create_array(env, &arr); if (status != napi_ok) return status; // Create a napi_value for 'hello' status = napi_create_string_utf8(env, "hello", NAPI_AUTO_LENGTH, &value); if (status != napi_ok) return status; // arr[123] = 'hello'; status = napi_set_element(env, arr, 123, value); if (status != napi_ok) return status;
Свойства можно получить, используя API, описанные в этом разделе. Рассмотрим следующий фрагмент JavaScript-кода:
const arr = []; const value = arr[123];
Следующее приблизительно соответствует API N-API:
napi_status status = napi_generic_failure; // const arr = [] napi_value arr, value; status = napi_create_array(env, &arr); if (status != napi_ok) return status; // const value = arr[123] status = napi_get_element(env, arr, 123, &value); if (status != napi_ok) return status;
Наконец, для повышения производительности на объекте можно определить несколько свойств. Рассмотрим следующий фрагмент JavaScript:
const obj = {};
Object.defineProperties(obj, {
'foo': { value: 123, writable: true, configurable: true, enumerable: true },
'bar': { value: 456, writable: true, configurable: true, enumerable: true }
});
Следующее приблизительно соответствует API N-API:
napi_status status = napi_status_generic_failure;
// const obj = {};
napi_value obj;
status = napi_create_object(env, &obj);
if (status != napi_ok) return status;
// Create napi_values for 123 and 456
napi_value fooValue, barValue;
status = napi_create_int32(env, 123, &fooValue);
if (status != napi_ok) return status;
status = napi_create_int32(env, 456, &barValue);
if (status != napi_ok) return status;
// Set the properties
napi_property_descriptor descriptors[] = {
{ "foo", NULL, NULL, NULL, NULL, fooValue, napi_default, NULL },
{ "bar", NULL, NULL, NULL, NULL, barValue, napi_default, NULL }
}
status = napi_define_properties(env,
obj,
sizeof(descriptors) / sizeof(descriptors[0]),
descriptors);
if (status != napi_ok) return status;
Структуры
napi_property_attributes
typedef enum {
napi_default = 0,
napi_writable = 1 << 0,
napi_enumerable = 1 << 1,
napi_configurable = 1 << 2,
// Used with napi_define_class to distinguish static properties
// from instance properties. Ignored by napi_define_properties.
napi_static = 1 << 10,
} napi_property_attributes;
Флаги, используемые для управления поведением свойств, заданных в объекте JavaScript. Помимо napi_static, они соответствуют атрибутам, перечисленным в разделе 6.1.7.1 спецификации языка ECMAScript ECMAScript Language Specification. Они могут быть одним или несколькими из следующих битовых флагов:
-
napi_default- Используется для указания, что для данного свойства не заданы явные атрибуты. По умолчанию свойство является только для чтения, не перечисляемым и не настраиваемым. -
napi_writable- Используется для указания, что данное свойство может быть изменено. -
napi_enumerable- Используется для указания, что данное свойство перечисляется. -
napi_configurable- Используется для указания, что данное свойство настраиваемое, как определено в разделе 6.1.7.1 спецификации языка ECMAScript ECMAScript Language Specification. -
napi_static- Используется для указания, что свойство будет определено как статическое свойство класса, а не свойство экземпляра, которое является по умолчанию. Используется только вnapi_define_class. Игнорируется вnapi_define_properties.
napi_property_descriptor
typedef struct {
// One of utf8name or name should be NULL.
const char* utf8name;
napi_value name;
napi_callback method;
napi_callback getter;
napi_callback setter;
napi_value value;
napi_property_attributes attributes;
void* data;
} napi_property_descriptor;
-
utf8name: НеобязательныйString, описывающий ключ свойства, закодированный в UTF8. Для свойства должен быть указан один изutf8nameилиname. -
name: Необязательныйnapi_value, указывающий на строку или символ JavaScript, используемые в качестве ключа свойства. Для свойства должен быть указан один изutf8nameилиname. -
value: Значение, извлекаемое при обращении к свойству для получения (если свойство является свойством данных). Если это значение передано, необходимо установитьgetter,setter,methodиdataв значениеNULL(поскольку эти члены не будут использоваться). -
getter: Функция, вызываемая при обращении к свойству для получения. Если это значение передано, необходимо установитьvalueиmethodв значениеNULL(поскольку эти члены не будут использоваться). Функция вызывается неявно средой выполнения, когда к свойству обращаются из кода JavaScript (или когда выполняется получение значения свойства с помощью вызова N-API). -
setter: Функция, вызываемая при обращении к свойству для установки. Если это значение передано, необходимо установитьvalueиmethodв значениеNULL(поскольку эти члены не будут использоваться). Функция вызывается неявно средой выполнения, когда свойство устанавливается из кода JavaScript (или когда выполняется установка значения свойства с помощью вызова N-API). -
method: Установите это значение, чтобы сделать свойствоvalueобъекта описателя свойства JavaScript-функцией, представленнойmethod. Если это значение передано, необходимо установитьvalue,getterиsetterв значениеNULL(поскольку эти члены не будут использоваться). -
attributes: Атрибуты, связанные с конкретным свойством. См.napi_property_attributes. -
data: Данные обратного вызова, передаваемые вmethod,getterиsetterпри вызове этой функции.
Функции
napi_get_property_names
napi_status napi_get_property_names(napi_env env,
napi_value object,
napi_value* result);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, из которого нужно извлечь свойства. -
[out] result:napi_valueпредставляющий массив значений JavaScript, которые представляют имена свойств объекта. API может использоваться для перебораresultс помощьюnapi_get_array_lengthиnapi_get_element.
Возвращает napi_ok в случае успешного выполнения API.
Это API возвращает имена перечисляемых свойств object в виде массива строк. Свойства object с ключом в виде символа не будут включены.
napi_get_all_property_names
napi_get_all_property_names(napi_env env,
napi_value object,
napi_key_collection_mode key_mode,
napi_key_filter key_filter,
napi_key_conversion key_conversion,
napi_value* result);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, из которого нужно извлечь свойства. -
[in] key_mode: Нужно ли извлекать свойства прототипа. -
[in] key_filter: Какие свойства извлекать (перечисляемые/доступные для чтения/изменения). -
[in] key_conversion: Нужно ли преобразовывать числовые ключи свойств в строки. -
[out] result: Anapi_valueпредставляющий массив JavaScript-значений, представляющих имена свойств объекта.napi_get_array_lengthиnapi_get_elementмогут использоваться для перебораresult.
Возвращает napi_ok в случае успешного выполнения API.
Это API возвращает массив, содержащий имена доступных свойств этого объекта.
napi_set_property
napi_status napi_set_property(napi_env env,
napi_value object,
napi_value key,
napi_value value);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, на котором нужно установить свойство. -
[in] key: Имя свойства, которое нужно установить. -
[in] value: Значение свойства.
Возвращает napi_ok в случае успешного выполнения API.
Это API устанавливает свойство на переданный Object.
napi_get_property
napi_status napi_get_property(napi_env env,
napi_value object,
napi_value key,
napi_value* result);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, из которого нужно извлечь свойство. -
[in] key: Имя свойства, которое нужно извлечь. -
[out] result: Значение свойства.
Возвращает napi_ok в случае успешного выполнения API.
Это API получает запрашиваемое свойство из переданного Object.
napi_has_property
napi_status napi_has_property(napi_env env,
napi_value object,
napi_value key,
bool* result);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, который нужно проверить. -
[in] key: Имя свойства, существование которого нужно проверить. -
[out] result: Существует ли свойство в объекте.
Возвращает napi_ok в случае успешного выполнения API.
Это API проверяет, содержит ли переданный Object указанное свойство.
napi_delete_property
napi_status napi_delete_property(napi_env env,
napi_value object,
napi_value key,
bool* result);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, который нужно проверить. -
[in] key: Имя свойства, которое нужно удалить. -
[out] result: Удалось ли удалить свойство.resultможно необязательно игнорировать, передаваяNULL.
Возвращает napi_ok в случае успешного выполнения API.
Это API пытается удалить key собственное свойство из object.
napi_has_own_property
napi_status napi_has_own_property(napi_env env,
napi_value object,
napi_value key,
bool* result);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, который нужно проверить. -
[in] key: Имя собственного свойства, существование которого нужно проверить. -
[out] result: Существует ли собственное свойство в объекте.
Возвращает napi_ok в случае успешного выполнения API.
Это API проверяет, содержит ли переданный Object указанное собственное свойство. key должен быть строкой или Symbol, в противном случае будет выброшено исключение. N-API не будет выполнять преобразование между типами данных.
napi_set_named_property
napi_status napi_set_named_property(napi_env env,
napi_value object,
const char* utf8Name,
napi_value value);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, на котором нужно установить свойство. -
[in] utf8Name: Имя свойства, которое нужно установить. -
[in] value: Значение свойства.
Возвращает napi_ok в случае успешного выполнения API.
Этот метод эквивалентен вызову napi_set_property со строкой, преобразованной в napi_value созданный из переданной строки в utf8Name.
napi_get_named_property
napi_status napi_get_named_property(napi_env env,
napi_value object,
const char* utf8Name,
napi_value* result);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, из которого нужно извлечь свойство. -
[in] utf8Name: Имя свойства, которое нужно получить. -
[out] result: Значение свойства.
Возвращает napi_ok в случае успешного выполнения API.
Этот метод эквивалентен вызову napi_get_property со строкой, преобразованной в napi_value созданный из переданной строки в utf8Name.
napi_has_named_property
napi_status napi_has_named_property(napi_env env,
napi_value object,
const char* utf8Name,
bool* result);
-
[in] env: Среда, в которой вызывается вызов N-API. -
[in] object: Объект, который нужно проверить. -
[in] utf8Name: Имя свойства, существование которого нужно проверить. -
[out] result: Существует ли свойство в объекте.
Возвращает napi_ok в случае успешного выполнения API.
Этот метод эквивалентен вызову napi_has_property со значением napi_value, созданным из переданной строки как utf8Name.
napi_set_element
napi_status napi_set_element(napi_env env,
napi_value object,
uint32_t index,
napi_value value);
-
[in] env: Окружение, в котором вызывается вызов N-API. -
[in] object: Объект, свойства которого нужно установить. -
[in] index: Индекс свойства для установки. -
[in] value: Значение свойства.
Возвращает napi_ok при успешном выполнении API.
Этот API устанавливает элемент в Object.
napi_get_element
napi_status napi_get_element(napi_env env,
napi_value object,
uint32_t index,
napi_value* result);
-
[in] env: Окружение, в котором вызывается вызов N-API. -
[in] object: Объект, из которого нужно извлечь свойство. -
[in] index: Индекс свойства для извлечения. -
[out] result: Значение свойства.
Возвращает napi_ok при успешном выполнении API.
Этот API извлекает элемент по указанному индексу.
napi_has_element
napi_status napi_has_element(napi_env env,
napi_value object,
uint32_t index,
bool* result);
-
[in] env: Окружение, в котором вызывается вызов N-API. -
[in] object: Объект для запроса. -
[in] index: Индекс свойства для проверки существования. -
[out] result: Существует ли свойство в объекте.
Возвращает napi_ok при успешном выполнении API.
Этот API возвращает, есть ли элемент по указанному индексу в переданном Object.
napi_delete_element
napi_status napi_delete_element(napi_env env,
napi_value object,
uint32_t index,
bool* result);
-
[in] env: Окружение, в котором вызывается вызов N-API. -
[in] object: Объект для запроса. -
[in] index: Индекс свойства для удаления. -
[out] result: Удаление элемента прошло успешно или нет.resultможно необязательно игнорировать, передавNULL.
Возвращает napi_ok при успешном выполнении API.
Этот API пытается удалить указанный index из object.
napi_define_properties
napi_status napi_define_properties(napi_env env,
napi_value object,
size_t property_count,
const napi_property_descriptor* properties);
-
[in] env: Окружение, в котором вызывается вызов N-API. -
[in] object: Объект, из которого извлекаются свойства. -
[in] property_count: Количество элементов в массивеproperties. -
[in] properties: Массив описателей свойств.
Возвращает napi_ok при успешном выполнении API.
Этот метод позволяет эффективно определять несколько свойств в заданном объекте. Свойства определяются с помощью описателей свойств (см. napi_property_descriptor). Этот API последовательно устанавливает свойства в объект, как определено в DefineOwnProperty() (описано в Разделе 9.1.6 спецификации ECMAScript).
Работа с JavaScript функциями
N-API предоставляет набор API, позволяющий JavaScript-коду вызывать нативный код. API N-API, поддерживающие обратные вызовы в нативный код, принимают в качестве аргумента функции обратного вызова типа napi_callback. Когда JavaScript-виртуальная машина вызывает нативный код, вызывается функция napi_callback.
- Получить информацию о контексте, в котором был вызван обратный вызов.
- Получить аргументы, переданные в обратный вызов.
- Возвратить значение
napi_valueиз обратного вызова.
Кроме того, N-API предоставляет набор функций для вызова JavaScript-функций из нативного кода. Можно вызвать функцию как обычный JavaScript-вызов или как конструктор.
Любые данные, не являющиеся NULL и передаваемые в этот API через поле data элементов napi_property_descriptor, могут быть связаны с object и освобождены при сборке мусора object, передав object и данные в napi_add_finalizer.
napi_call_function
napi_status napi_call_function(napi_env env,
napi_value recv,
napi_value func,
int argc,
const napi_value* argv,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] recv: Объектthis, переданный вызываемой функции. -
[in] func: Значениеnapi_value, представляющее JavaScript-функцию для вызова. -
[in] argc: Количество элементов в массивеargv. -
[in] argv: Массив значенийnapi_values, представляющих JavaScript-значения, переданные в функцию в качестве аргументов. -
[out] result: Значениеnapi_value, представляющее возвращаемый JavaScript-объект.
Возвращает napi_ok при успешном выполнении API.
Этот метод позволяет вызывать JavaScript-функцию из нативного дополнения. Это основной механизм вызова из нативного кода дополнения в JavaScript. Для специального случая вызова JavaScript после асинхронной операции см. napi_make_callback.
Пример использования может выглядеть следующим образом. Рассмотрим следующий JavaScript-фрагмент:
function AddTwo(num) {
return num + 2;
}
Затем, указанную функцию можно вызвать из нативного дополнения следующим кодом:
// Get the function named "AddTwo" on the global object napi_value global, add_two, arg; napi_status status = napi_get_global(env, &global); if (status != napi_ok) return; status = napi_get_named_property(env, global, "AddTwo", &add_two); if (status != napi_ok) return; // const arg = 1337 status = napi_create_int32(env, 1337, &arg); if (status != napi_ok) return; napi_value* argv = &arg; size_t argc = 1; // AddTwo(arg); napi_value return_val; status = napi_call_function(env, global, add_two, argc, argv, &return_val); if (status != napi_ok) return; // Convert the result back to a native type int32_t result; status = napi_get_value_int32(env, return_val, &result); if (status != napi_ok) return;
napi_create_function
napi_status napi_create_function(napi_env env,
const char* utf8name,
size_t length,
napi_callback cb,
void* data,
napi_value* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] utf8Name: Название функции, закодированное в UTF8. Это видно в JavaScript как свойствоnameнового объекта функции. -
[in] length: Длина имени функции в байтах илиNAPI_AUTO_LENGTH, если оно завершается нулем. -
[in] cb: Нативная функция, которая должна вызываться при вызове этого объекта функции. -
[in] data: Контекст данных, предоставляемый пользователем. Он будет передан обратно в функцию при её последующем вызове. -
[out] result: Значениеnapi_value, представляющее JavaScript-объект функции, созданной функции.
Возвращает napi_ok при успешном выполнении API.
Этот API позволяет автору дополнения создавать объект функции в нативном коде. Это основной механизм вызова в нативный код дополнения из JavaScript.
Новое созданная функция не отображается автоматически в скрипте после этого вызова. Вместо этого нужно явно установить свойство на любой объект, видимый JavaScript, чтобы сделать функцию доступной в скрипте.
Чтобы экспортировать функцию в качестве части экспорта модуля дополнения, установите созданную функцию в объект экспорта.
napi_value SayHello(napi_env env, napi_callback_info info) {
printf("Hello\n");
return NULL;
}
napi_value Init(napi_env env, napi_value exports) {
napi_status status;
napi_value fn;
status = napi_create_function(env, NULL, 0, SayHello, NULL, &fn);
if (status != napi_ok) return NULL;
status = napi_set_named_property(env, exports, "sayHello", fn);
if (status != napi_ok) return NULL;
return exports;
}
NAPI_MODULE(NODE_GYP_MODULE_NAME, Init)
После написания кода, дополнение может использоваться в JavaScript следующим образом:
const myaddon = require('./addon');
myaddon.sayHello();
Строка, переданная в require(), является именем целевого объекта в binding.gyp, отвечающего за создание файла .node.
Любые не-NULL данные, переданные в этот API через параметр data, могут быть связаны с созданной JavaScript-функцией (которая возвращается в параметре result) и освобождаться при сборе мусора функции, передав и JavaScript-функцию и данные в napi_add_finalizer.
JavaScript-функции описаны в Разделе 19.2 спецификации ECMAScript Language Specification.
napi_get_cb_info
napi_status napi_get_cb_info(napi_env env,
napi_callback_info cbinfo,
size_t* argc,
napi_value* argv,
napi_value* thisArg,
void** data)
-
[in] env: Окружение, в котором вызывается API. -
[in] cbinfo: Информация о обратном вызове, переданная в функцию обратного вызова. -
[in-out] argc: Указывает размер массиваargvи получает фактическое количество аргументов. -
[out] argv: Буфер, в который копируются значенияnapi_valueпредставляющие аргументы. Если аргументов больше, чем указанное количество, копируются только запрошенные аргументы. Если предоставлено меньше аргументов, чем заявлено, оставшаяся частьargvзаполняется значениямиnapi_value, представляющимиundefined. -
[out] this: Получает JavaScript-аргументthisдля вызова. -
[out] data: Получает указатель на данные для обратного вызова.
Возвращает napi_ok при успешном выполнении API.
Этот метод используется внутри функции обратного вызова для извлечения деталей вызова, таких как аргументы и указатель this из заданной информации о обратном вызове.
napi_get_new_target
napi_status napi_get_new_target(napi_env env,
napi_callback_info cbinfo,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] cbinfo: Информация о обратном вызове, переданная в функцию обратного вызова. -
[out] result:new.targetвызова конструктора.
Возвращает napi_ok при успешном выполнении API.
Этот API возвращает new.target вызова конструктора. Если текущий обратный вызов не является вызовом конструктора, результат — NULL.
napi_new_instance
napi_status napi_new_instance(napi_env env,
napi_value cons,
size_t argc,
napi_value* argv,
napi_value* result)
-
[in] env: Среда, в которой вызывается API. -
[in] cons:napi_value, представляющий JavaScript-функцию, вызываемую как конструктор. -
[in] argc: Количество элементов в массивеargv. -
[in] argv: Массив JavaScript-значений в видеnapi_value, представляющих аргументы конструктора. -
[out] result:napi_value, представляющий возвращаемый JavaScript-объект, в данном случае — созданный объект.
Этот метод используется для создания нового JavaScript-значения с помощью заданного napi_value, который представляет конструктор объекта. Например, рассмотрим следующий фрагмент:
function MyObject(param) {
this.param = param;
}
const arg = 'hello';
const value = new MyObject(arg);
Следующее можно приблизительно реализовать в N-API с помощью следующего фрагмента:
// Get the constructor function MyObject napi_value global, constructor, arg, value; napi_status status = napi_get_global(env, &global); if (status != napi_ok) return; status = napi_get_named_property(env, global, "MyObject", &constructor); if (status != napi_ok) return; // const arg = "hello" status = napi_create_string_utf8(env, "hello", NAPI_AUTO_LENGTH, &arg); if (status != napi_ok) return; napi_value* argv = &arg; size_t argc = 1; // const value = new MyObject(arg) status = napi_new_instance(env, constructor, argc, argv, &value);
Возвращает napi_ok, если API выполнилась успешно.
Обёртка объекта
N-API предоставляет способ «обёртки» C++-классов и экземпляров, чтобы конструктор класса и его методы можно было вызывать из JavaScript.
- API
napi_define_classопределяет JavaScript-класс с конструктором, статическими свойствами и методами, а также свойствами и методами экземпляров, соответствующими C++-классу. - Когда JavaScript-код вызывает конструктор, обратный вызов конструктора использует
napi_wrapдля обёртки нового C++-экземпляра в JavaScript-объект, а затем возвращает объект-обёртку. - Когда JavaScript-код вызывает метод или обработчик доступа к свойству класса, вызывается соответствующая
napi_callbackC++-функция. Для обратного вызова экземпляраnapi_unwrapполучает C++-экземпляр, являющийся объектом вызова.
Для обёрнутых объектов может быть сложно отличить вызов функции на прототипе класса от вызова функции на экземпляре класса. Общим шаблоном для решения этой проблемы является сохранение постоянной ссылки на конструктор класса для последующих instanceof проверок.
napi_value MyClass_constructor = NULL;
status = napi_get_reference_value(env, MyClass::es_constructor, &MyClass_constructor);
assert(napi_ok == status);
bool is_instance = false;
status = napi_instanceof(env, es_this, MyClass_constructor, &is_instance);
assert(napi_ok == status);
if (is_instance) {
// napi_unwrap() ...
} else {
// otherwise...
}
Ссылка должна быть освобождена, когда она больше не требуется.
napi_define_class
napi_status napi_define_class(napi_env env,
const char* utf8name,
size_t length,
napi_callback constructor,
void* data,
size_t property_count,
const napi_property_descriptor* properties,
napi_value* result);
-
[in] env: Среда, в которой вызывается API. -
[in] utf8name: Имя JavaScript-функции-конструктора; не обязательно совпадает с именем C++-класса, хотя рекомендуется для ясности. -
[in] length: Длинаutf8nameв байтах илиNAPI_AUTO_LENGTH, если она имеет нуль-терминатор. -
[in] constructor: Функция обратного вызова, обрабатывающая создание экземпляров класса. (Это должен быть статический метод класса, а не собственно C++-конструктор). -
[in] data: Дополнительные данные, передаваемые в обратный вызов конструктора как свойствоdataинформации о вызове. -
[in] property_count: Число элементов в массиве аргументовproperties. -
[in] properties: Массив описателей свойств, описывающих статические и экземплярные данные, аксессоры и методы класса. См.napi_property_descriptor. -
[out] result:napi_valueпредставляющая функцию-конструктор класса.
Возвращает napi_ok, если API выполнилась успешно.
Определяет JavaScript-класс, соответствующий C++-классу, включая:
- JavaScript-функцию-конструктор, имеющую имя класса и вызывающую предоставленный C++-обратный вызов конструктора.
- Свойства в функции-конструкторе, соответствующие статическим данным, аксессорам и методам C++-класса (определяются описателями свойств с атрибутом
napi_static). - Свойства в объекте
prototypeфункции-конструктора, соответствующие нестатическим данным, аксессорам и методам C++-класса (определяются описателями свойств без атрибутаnapi_static).
C++-обратный вызов конструктора должен быть статическим методом класса, который вызывает фактический конструктор класса, затем обёртывает новый C++-экземпляр в JavaScript-объект и возвращает объект обёртки. Подробности см. в napi_wrap().
Функция-конструктор JavaScript, возвращаемая из napi_define_class, часто сохраняется и используется позднее для создания новых экземпляров класса из нативного кода и/или проверки, являются ли предоставленные значения экземплярами класса. В этом случае, чтобы предотвратить сборку мусора функции, создайте постоянную ссылку на неё, используя napi_create_reference, и убедитесь, что счётчик ссылок остаётся >= 1.
Любые не-NULL данные, передаваемые в этот API через параметр data или через поле data элементов массива napi_property_descriptor, могут быть связаны с результирующим JavaScript-конструктором (который возвращается в параметре result) и освобождаться при сборе мусора класса путём передачи как JavaScript-функции, так и данных в napi_add_finalizer.
napi_wrap
napi_status napi_wrap(napi_env env,
napi_value js_object,
void* native_object,
napi_finalize finalize_cb,
void* finalize_hint,
napi_ref* result);
-
[in] env: Среда, в которой вызывается API. -
[in] js_object: JavaScript-объект, который будет обёрткой для нативного объекта. -
[in] native_object: Нативный экземпляр, который будет обёрнут в JavaScript-объект. -
[in] finalize_cb: Необязательный нативный обратный вызов, который может использоваться для освобождения нативного экземпляра, когда JavaScript-объект готов к сбору мусора. -
[in] finalize_hint: Необязательный контекстный подсказчик, передаваемый обратному вызову завершения. -
[out] result: Необязательная ссылка на обёрнутый объект.
Возвращает napi_ok, если API выполнилась успешно.
Обёртка нативного экземпляра в JavaScript-объект. Нативный экземпляр можно получить позже, используя napi_unwrap().
Когда JavaScript-код вызывает конструктор класса, определённого с помощью napi_define_class(), вызывается napi_callback для конструктора. После создания экземпляра нативного класса обратный вызов должен вызвать napi_wrap() для обёртки только что созданного экземпляра в уже созданный JavaScript-объект, являющийся параметром this обратного вызова конструктора. (Этот объект this был создан из prototype функции-конструктора, поэтому в нём уже определены все свойства и методы экземпляра).
Обычно при обёртке экземпляра класса должен предоставляться обратный вызов завершения, который просто удаляет нативный экземпляр, полученный как аргумент data обратного вызова завершения.
Необязательная возвращаемая ссылка изначально является слабой ссылкой, то есть её счётчик ссылок равен 0. Обычно этот счётчик ссылок временно увеличивается во время асинхронных операций, требующих сохранения валидности экземпляра.
Внимание: необязательная возвращаемая ссылка (если получена) должна быть удалена с помощью napi_delete_reference ТОЛЬКО в ответ на вызов обратного вызова завершения. Если она удалена до этого, то обратный вызов завершения может никогда не быть вызван. Поэтому, при получении ссылки также требуется обратный вызов завершения для правильного удаления ссылки.
Вызов napi_wrap() второй раз для объекта вернёт ошибку. Чтобы связать другой нативный экземпляр с объектом, сначала используйте napi_remove_wrap().
napi_unwrap
napi_status napi_unwrap(napi_env env,
napi_value js_object,
void** result);
-
[in] env: Среда, в которой вызывается API. -
[in] js_object: Объект, связанный с нативным экземпляром. -
[out] result: Указатель на обёрнутый нативный экземпляр.
Возвращает napi_ok, если API выполнилась успешно.
Получение нативного экземпляра, который ранее был обёрнут в JavaScript-объект с помощью napi_wrap().
Когда JavaScript-код вызывает метод или обработчик доступа к свойству класса, вызывается соответствующая napi_callback. Если обратный вызов предназначен для метода или аксессора экземпляра, то аргумент this обратного вызова — это объект-обёртка; обёрнутый C++-экземпляр, являющийся объектом вызова, может быть получен вызовом napi_unwrap() для объекта-обёртки.
napi_remove_wrap
napi_status napi_remove_wrap(napi_env env,
napi_value js_object,
void** result);
-
[in] env: Среда, в которой вызывается API. -
[in] js_object: Объект, связанный с нативным экземпляром. -
[out] result: Указатель на обёрнутый нативный экземпляр.
Возвращает napi_ok, если API выполнилась успешно.
Получение нативного экземпляра, который ранее был обёрнут в JavaScript-объект js_object с помощью napi_wrap() и удаление обёртки. Если обратный вызов завершения был связан с обёрткой, он больше не будет вызываться при сборе мусора JavaScript-объекта.
napi_add_finalizer
napi_status napi_add_finalizer(napi_env env,
napi_value js_object,
void* native_object,
napi_finalize finalize_cb,
void* finalize_hint,
napi_ref* result);
-
[in] env: Среда, в которой вызывается API. -
[in] js_object: JavaScript-объект, к которому будет прикреплены нативные данные. -
[in] native_object: Нативные данные, которые будут прикреплены к JavaScript-объекту. -
[in] finalize_cb: Нативный обратный вызов, который будет использован для освобождения нативных данных, когда JavaScript-объект готов к сбору мусора. -
[in] finalize_hint: Необязательный контекстный подсказчик, передаваемый обратному вызову завершения. -
[out] result: Необязательная ссылка на JavaScript-объект.
Возвращает napi_ok, если API выполнилась успешно.
Добавляет обратный вызов napi_finalize, который будет вызван, когда JavaScript-объект в js_object готов к сбору мусора. Этот API похож на napi_wrap(), за исключением того, что
- нативные данные нельзя получить позже с помощью
napi_unwrap(), - их нельзя удалить позже с помощью
napi_remove_wrap(), и - API можно вызывать несколько раз с разными данными, чтобы прикрепить каждый из них к JavaScript-объекту.
Внимание: необязательная возвращаемая ссылка (если получена) должна быть удалена с помощью napi_delete_reference ТОЛЬКО в ответ на вызов обратного вызова finalize. Если она удалена до этого, обратный вызов finalize может никогда не быть вызван. Поэтому при получении ссылки также требуется обратный вызов finalize для правильного удаления ссылки.
Простые асинхронные операции
Модули дополнений часто нуждаются в использовании асинхронных помощников из libuv в рамках своей реализации. Это позволяет им планировать выполнение работы асинхронно, чтобы их методы могли возвращаться до завершения работы. Это важно, чтобы избежать блокировки общего выполнения приложения Node.js.
N-API предоставляет интерфейс с ABI-стабильностью для этих поддерживающих функций, охватывающий наиболее распространённые случаи асинхронного использования.
N-API определяет структуру napi_work, которая используется для управления асинхронными рабочими процессами. Экземпляры создаются/удаляются с помощью napi_create_async_work и napi_delete_async_work.
Обратные вызовы execute и complete являются функциями, которые будут вызваны, когда исполнитель готов к выполнению и когда он завершит свою задачу соответственно.
Функция execute должна избегать выполнения любых вызовов N-API, которые могут привести к выполнению JavaScript или взаимодействию с объектами JavaScript. Чаще всего любой код, которому необходимо выполнить вызовы N-API, должен быть выполнен в обратном вызове complete.
Эти функции реализуют следующие интерфейсы:
typedef void (*napi_async_execute_callback)(napi_env env,
void* data);
typedef void (*napi_async_complete_callback)(napi_env env,
napi_status status,
void* data);
При вызове этих методов параметр data будет содержать предоставляемые дополнением данные void*, которые были переданы в вызов napi_create_async_work.
После создания асинхронный рабочий процесс может быть помещен в очередь для выполнения с помощью функции napi_queue_async_work:
napi_status napi_queue_async_work(napi_env env,
napi_async_work work);
Если работу необходимо отменить до начала выполнения, можно использовать napi_cancel_async_work.
После вызова napi_cancel_async_work, обратный вызов complete будет вызван со значением состояния napi_cancelled. Работа не должна быть удалена до вызова обратного вызова complete, даже если она была отменена.
napi_create_async_work
napi_status napi_create_async_work(napi_env env,
napi_value async_resource,
napi_value async_resource_name,
napi_async_execute_callback execute,
napi_async_complete_callback complete,
void* data,
napi_async_work* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] async_resource: Необязательный объект, связанный с асинхронной работой, который будет передан возможнымasync_hooksinitхукам. -
[in] async_resource_name: Идентификатор типа ресурса, предоставляемого для диагностической информации, предоставляемой APIasync_hooks. -
[in] execute: Нативная функция, которая должна вызываться для асинхронного выполнения логики. Эта функция вызывается из потока пула рабочих процессов и может выполняться параллельно с основным потоком обработки событий. -
[in] complete: Нативная функция, которая будет вызываться при завершении или отмене асинхронной логики. Эта функция вызывается из основного потока обработки событий. -
[in] data: Предоставленные пользователем данные контекста. Они будут переданы обратно функциям execute и complete. -
[out] result:napi_async_work*, который является дескриптором созданного асинхронного рабочего процесса.
Возвращает napi_ok при успешном выполнении API.
Этот API выделяет объект работы, используемый для асинхронного выполнения логики. Он должен быть освобождён с помощью napi_delete_async_work, когда работа больше не требуется.
async_resource_name должен быть строкой с завершающим нулем, закодированной в UTF-8.
Идентификатор async_resource_name предоставляется пользователем и должен отражать тип выполняемой асинхронной работы. Также рекомендуется использовать именование для идентификатора, например, включив имя модуля. Дополнительную информацию см. в async_hooks документации.
napi_delete_async_work
napi_status napi_delete_async_work(napi_env env,
napi_async_work work);
-
[in] env: Окружение, в котором вызывается API. -
[in] work: Дескриптор, возвращённый вызовомnapi_create_async_work.
Возвращает napi_ok при успешном выполнении API.
Этот API освобождает ранее выделенный объект работы.
Этот API может быть вызван даже при наличии ожидающей JavaScript-ошибки.
napi_queue_async_work
napi_status napi_queue_async_work(napi_env env,
napi_async_work work);
-
[in] env: Окружение, в котором вызывается API. -
[in] work: Дескриптор, возвращённый вызовомnapi_create_async_work.
Возвращает napi_ok при успешном выполнении API.
Этот API запрашивает планирование ранее выделенной работы для выполнения.
napi_cancel_async_work
napi_status napi_cancel_async_work(napi_env env,
napi_async_work work);
-
[in] env: Окружение, в котором вызывается API. -
[in] work: Дескриптор, возвращённый вызовомnapi_create_async_work.
Возвращает napi_ok при успешном выполнении API.
Этот API отменяет запланированную работу, если она ещё не начата. Если она уже начала выполняться, её нельзя отменить, и будет возвращено napi_generic_failure. При успешной отмене, обратный вызов complete будет вызван со значением состояния napi_cancelled. Работа не должна быть удалена до вызова обратного вызова complete, даже если она была успешно отменена.
Этот API может быть вызван даже при наличии ожидающей JavaScript-ошибки.
Пользовательские асинхронные операции
Простые асинхронные API выше могут быть неподходящими для всех сценариев. При использовании других асинхронных механизмов необходимы следующие API, чтобы гарантировать, что асинхронная операция правильно отслеживается средой выполнения.
napi_async_init
napi_status napi_async_init(napi_env env,
napi_value async_resource,
napi_value async_resource_name,
napi_async_context* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] async_resource: Необязательный объект, связанный с асинхронной работой, который будет передан возможнымasync_hooksinitхукам. -
[in] async_resource_name: Идентификатор типа ресурса, предоставляемого для диагностической информации, предоставляемой APIasync_hooks. -
[out] result: Инициализированный асинхронный контекст.
Возвращает napi_ok при успешном выполнении API.
napi_async_destroy
napi_status napi_async_destroy(napi_env env,
napi_async_context async_context);
-
[in] env: Окружение, в котором вызывается API. -
[in] async_context: Асинхронный контекст, который необходимо уничтожить.
Возвращает napi_ok при успешном выполнении API.
Этот API может быть вызван даже при наличии ожидающей JavaScript-ошибки.
napi_make_callback
napi_status napi_make_callback(napi_env env,
napi_async_context async_context,
napi_value recv,
napi_value func,
int argc,
const napi_value* argv,
napi_value* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] async_context: Контекст асинхронной операции, вызывающей обратный вызов. Обычно это значение, полученное ранее изnapi_async_init. Однако также разрешено значениеNULL, что указывает на использование текущего асинхронного контекста (если он есть) для обратного вызова. -
[in] recv: Объектthis, переданный вызываемой функции. -
[in] func:napi_valueпредставляющий вызываемую JavaScript-функцию. -
[in] argc: Количество элементов в массивеargv. -
[in] argv: Массив JavaScript-значений какnapi_value, представляющих аргументы функции. -
[out] result:napi_valueпредставляющий возвращаемый JavaScript-объект.
Возвращает napi_ok при успешном выполнении API.
Этот метод позволяет вызывать объект JavaScript-функции из нативного дополнения. Этот API похож на napi_call_function. Однако он используется для вызова из нативного кода обратно в JavaScript после возвращения из асинхронной операции (когда в стеке нет другого скрипта). Это довольно простой обертка над node::MakeCallback.
Обратите внимание, что не обязательно использовать napi_make_callback внутри napi_async_complete_callback; в этом случае асинхронный контекст обратного вызова уже настроен, поэтому прямой вызов napi_call_function является достаточным и соответствующим. Использование функции napi_make_callback может потребоваться при реализации пользовательского асинхронного поведения, не использующего napi_create_async_work.
napi_open_callback_scope
NAPI_EXTERN napi_status napi_open_callback_scope(napi_env env,
napi_value resource_object,
napi_async_context context,
napi_callback_scope* result)
-
[in] env: Окружение, в котором вызывается API. -
[in] resource_object: Объект, связанный с асинхронной работой, который будет передан возможнымasync_hooksinitхукам. -
[in] context: Контекст асинхронной операции, вызывающей обратный вызов. Это должно быть значение, полученное ранее изnapi_async_init. -
[out] result: Созданный контекст.
Существуют случаи (например, разрешение промисов), когда необходимо иметь эквивалент контекста, связанного с обратным вызовом, при выполнении определённых вызовов N-API. Если на стеке нет другого скрипта, функции napi_open_callback_scope и napi_close_callback_scope могут использоваться для открытия/закрытия необходимого контекста.
napi_close_callback_scope
NAPI_EXTERN napi_status napi_close_callback_scope(napi_env env,
napi_callback_scope scope)
-
[in] env: Окружение, в котором вызывается API. -
[in] scope: Контекст, который нужно закрыть.
Этот API может быть вызван даже при наличии ожидающей JavaScript-ошибки.
Управление версиями
napi_get_node_version
typedef struct {
uint32_t major;
uint32_t minor;
uint32_t patch;
const char* release;
} napi_node_version;
napi_status napi_get_node_version(napi_env env,
const napi_node_version** version);
-
[in] env: Окружение, в котором вызывается API. -
[out] version: Указатель на информацию о версии Node.js.
Возвращает napi_ok в случае успешного выполнения API.
Функция заполняет структуру version значениями основной, дополнительной и патч-версии Node.js, а поле release — значением process.release.name.
Возвращаемый буфер статически выделяется и не требует освобождения.
napi_get_version
napi_status napi_get_version(napi_env env,
uint32_t* result);
-
[in] env: Окружение, в котором вызывается API. -
[out] result: Наивысшая поддерживаемая версия N-API.
Возвращает napi_ok в случае успешного выполнения API.
Этот API возвращает наивысшую поддерживаемую версию N-API в среде выполнения Node.js. N-API планируется как расширяемая спецификация, так что более новые версии Node.js могут поддерживать дополнительные функции API. Чтобы разрешить плагину использовать новую функцию при работе с версиями Node.js, которые её поддерживают, а также обеспечивать отказоустойчивость при работе с версиями, которые её не поддерживают:
- Вызовите
napi_get_version()для определения доступности API. - Если доступно, динамически загрузите указатель на функцию с помощью
uv_dlsym(). - Используйте загруженный указатель для вызова функции.
- Если функция недоступна, предоставьте альтернативную реализацию, которая её не использует.
Управление памятью
napi_adjust_external_memory
NAPI_EXTERN napi_status napi_adjust_external_memory(napi_env env,
int64_t change_in_bytes,
int64_t* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] change_in_bytes: Изменение объёма внешней памяти, поддерживаемой JavaScript-объектами. -
[out] result: Скорректированное значение
Возвращает napi_ok в случае успешного выполнения API.
Эта функция даёт V8 указание на объём внешней памяти, поддерживаемой JavaScript-объектами (то есть JavaScript-объект, который указывает на свою память, выделенную нативным модулем). Регистрация внешней памяти будет вызывать глобальные сборки мусора чаще, чем в противном случае.
Промисы
N-API предоставляет средства для создания Promise объектов, как описано в разделе 25.4 спецификации ECMA. Промисы реализуются как пара объектов. Когда промис создаётся с помощью napi_create_promise(), создаётся объект "отложенный" (deferred), который возвращается вместе с Promise. Объект "отложенный" связан с созданным Promise и является единственным способом разрешить или отклонить Promise с помощью napi_resolve_deferred() или napi_reject_deferred(). Объект "отложенный", созданный napi_create_promise(), освобождается napi_resolve_deferred() или napi_reject_deferred(). Объект Promise может быть возвращён в JavaScript, где он может использоваться обычным образом.
Например, чтобы создать промис и передать его асинхронному работнику:
napi_deferred deferred; napi_value promise; napi_status status; // Create the promise. status = napi_create_promise(env, &deferred, &promise); if (status != napi_ok) return NULL; // Pass the deferred to a function that performs an asynchronous action. do_something_asynchronous(deferred); // Return the promise to JS return promise;
Функция do_something_asynchronous() выполнит свою асинхронную операцию, а затем разрешит или отклонит отложенный (deferred) объект, тем самым завершив промис и освободив deferred:
napi_deferred deferred;
napi_value undefined;
napi_status status;
// Create a value with which to conclude the deferred.
status = napi_get_undefined(env, &undefined);
if (status != napi_ok) return NULL;
// Resolve or reject the promise associated with the deferred depending on
// whether the asynchronous action succeeded.
if (asynchronous_action_succeeded) {
status = napi_resolve_deferred(env, deferred, undefined);
} else {
status = napi_reject_deferred(env, deferred, undefined);
}
if (status != napi_ok) return NULL;
// At this point the deferred has been freed, so we should assign NULL to it.
deferred = NULL;
napi_create_promise
napi_status napi_create_promise(napi_env env,
napi_deferred* deferred,
napi_value* promise);
-
[in] env: Окружение, в котором вызывается API. -
[out] deferred: Созданный объект "отложенный" (deferred), который позже можно передать вnapi_resolve_deferred()илиnapi_reject_deferred()для разрешения или отклонения связанного промиса. -
[out] promise: JavaScript-промис, связанный с объектом "отложенный".
Возвращает napi_ok в случае успешного выполнения API.
Этот API создаёт объект "отложенный" и JavaScript-промис.
napi_resolve_deferred
napi_status napi_resolve_deferred(napi_env env,
napi_deferred deferred,
napi_value resolution);
-
[in] env: Окружение, в котором вызывается API. -
[in] deferred: Объект "отложенный" (deferred), связанный с промисом, который нужно разрешить. -
[in] resolution: Значение, с помощью которого разрешить промис.
Этот API разрешает JavaScript-промис с помощью объекта "отложенный" (deferred), с которым он связан. Таким образом, его можно использовать только для разрешения JavaScript-промисов, для которых доступен соответствующий объект "отложенный". Это означает, что промис должен быть создан с помощью napi_create_promise() и объект "отложенный", возвращённый из этого вызова, должен быть сохранён, чтобы быть передан в этот API.
Объект "отложенный" освобождается при успешном выполнении.
napi_reject_deferred
napi_status napi_reject_deferred(napi_env env,
napi_deferred deferred,
napi_value rejection);
-
[in] env: Окружение, в котором вызывается API. -
[in] deferred: Объект "отложенный" (deferred), связанный с промисом, который нужно отклонить. -
[in] rejection: Значение, с помощью которого отклонить промис.
Этот API отклоняет JavaScript-промис с помощью объекта "отложенный" (deferred), с которым он связан. Таким образом, его можно использовать только для отклонения JavaScript-промисов, для которых доступен соответствующий объект "отложенный". Это означает, что промис должен быть создан с помощью napi_create_promise() и объект "отложенный", возвращённый из этого вызова, должен быть сохранён, чтобы быть передан в этот API.
Объект "отложенный" освобождается при успешном выполнении.
napi_is_promise
napi_status napi_is_promise(napi_env env,
napi_value promise,
bool* is_promise);
-
[in] env: Окружение, в котором вызывается API. -
[in] promise: Промис для проверки -
[out] is_promise: Флаг, указывающий, является лиpromiseнативным объектом промиса — то есть объектом промиса, созданным основным движком.
Выполнение скрипта
N-API предоставляет API для выполнения строки JavaScript с помощью основного движка JavaScript.
napi_run_script
NAPI_EXTERN napi_status napi_run_script(napi_env env,
napi_value script,
napi_value* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] script: Строка JavaScript, содержащая скрипт для выполнения. -
[out] result: Результат выполнения скрипта.
Цикл событий libuv
N-API предоставляет функцию для получения текущего цикла событий, связанного с определённым napi_env.
napi_get_uv_event_loop
NAPI_EXTERN napi_status napi_get_uv_event_loop(napi_env env,
uv_loop_t** loop);
-
[in] env: Окружение, в котором вызывается API. -
[out] loop: Текущий экземпляр цикла libuv.
Асинхронные потокобезопасные вызовы функций
JavaScript-функции обычно могут вызываться только из основного потока нативного плагина. Если плагин создаёт дополнительные потоки, то функции N-API, требующие napi_env, napi_value, или napi_ref, не должны вызываться из этих потоков.
Когда плагин имеет дополнительные потоки, и JavaScript-функции нужно вызывать, основываясь на обработке, выполненной этими потоками, эти потоки должны взаимодействовать с основным потоком плагина, чтобы основной поток мог вызвать JavaScript-функцию от их имени. Потокобезопасные API предоставляют удобный способ сделать это.
Эти API предоставляют тип napi_threadsafe_function а также API для создания, уничтожения и вызова объектов этого типа. napi_create_threadsafe_function() создаёт постоянную ссылку на napi_value, который содержит JavaScript-функцию, которую можно вызывать из нескольких потоков. Вызовы происходят асинхронно. Это означает, что значения, с помощью которых будет вызываться JavaScript-обратный вызов, будут помещены в очередь, и для каждого значения в очереди в конечном итоге будет сделан вызов JavaScript-функции.
При создании napi_threadsafe_function можно предоставить обратный вызов napi_finalize. Этот обратный вызов будет вызван в главном потоке, когда потокобезопасная функция будет уничтожена. Он получает контекст и данные завершения, предоставленные во время создания, и предоставляет возможность для очистки после потоков, например, вызвав uv_thread_join(). Важно, чтобы помимо основного потока цикла не оставалось потоков, использующих потокобезопасную функцию после завершения обратного вызова завершения.
Получить context, переданное при вызове napi_create_threadsafe_function(), можно с любой нити, вызвав napi_get_threadsafe_function_context().
napi_call_threadsafe_function() затем можно использовать для инициирования вызова в JavaScript. napi_call_threadsafe_function() принимает параметр, контролирующий, будет ли API работать блокирующим образом. Если он установлен в napi_tsfn_nonblocking, API работает неблокирующим образом, возвращая napi_queue_full, если очередь была заполнена, предотвращая успешное добавление данных в очередь. Если он установлен в napi_tsfn_blocking, API блокируется, пока в очереди не освободится место. napi_call_threadsafe_function() никогда не блокируется, если функция с защитой от множественных потоков была создана с максимальным размером очереди 0.
Фактический вызов в JavaScript контролируется обратным вызовом, переданным через параметр call_js_cb. call_js_cb вызывается в основной нити один раз для каждого значения, помещенного в очередь успешным вызовом napi_call_threadsafe_function(). Если такой обратный вызов не задан, используется обратный вызов по умолчанию, и полученный вызов JavaScript не будет иметь аргументов. Обратный вызов call_js_cb получает функцию JavaScript для вызова как napi_value в своих параметрах, а также указатель контекста void*, используемый при создании napi_threadsafe_function, и указатель на следующие данные, созданный одной из дополнительных нитей. Затем обратный вызов может использовать API, такой как napi_call_function() для вызова в JavaScript.
Обратный вызов также может быть вызван с env и call_js_cb, установленными в значение NULL, чтобы указать, что вызовы в JavaScript больше невозможны, в то время как в очереди остаются элементы, которые могут потребоваться освободить. Это обычно происходит, когда процесс Node.js завершается, в то время как функция с защитой от множественных потоков всё ещё активна.
Необязательно вызывать JavaScript через napi_make_callback(), поскольку N-API выполняет call_js_cb в контексте, соответствующем обратным вызовам.
В объект napi_threadsafe_function можно добавлять и удалять нити в течение его существования. Таким образом, помимо указания начального количества нитей при создании, napi_acquire_threadsafe_function можно вызвать, чтобы указать, что новая нить начнёт использовать функцию с защитой от множественных потоков. Аналогично, napi_release_threadsafe_function можно вызвать, чтобы указать, что существующая нить прекратит использование функции с защитой от множественных потоков.
Объекты napi_threadsafe_function уничтожаются, когда каждая нить, использующая объект, вызвала napi_release_threadsafe_function() или получила возвращаемый статус napi_closing в ответ на вызов napi_call_threadsafe_function. Очередь очищается перед уничтожением napi_threadsafe_function. Важно, чтобы napi_release_threadsafe_function() был последним вызовом API в сочетании с данным napi_threadsafe_function, потому что после завершения вызова нет гарантии, что napi_threadsafe_function всё ещё выделен. По той же причине важно, чтобы больше не использовалась функция с защитой от множественных потоков после получения возвращаемого значения napi_closing в ответ на вызов napi_call_threadsafe_function. Данные, связанные с napi_threadsafe_function, могут быть освобождены в его обратном вызове napi_finalize, переданном в napi_create_threadsafe_function().
После того, как количество нитей, использующих napi_threadsafe_function, достигнет нуля, другие нити не смогут начать использовать его, вызвав napi_acquire_threadsafe_function(). Фактически, все последующие API-вызовы, связанные с ним, кроме napi_release_threadsafe_function(), вернут значение ошибки napi_closing.
Функцию с защитой от множественных потоков можно "прервать", задав значение napi_tsfn_abort для napi_release_threadsafe_function(). Это заставит все последующие API, связанные с функцией с защитой от множественных потоков, кроме napi_release_threadsafe_function(), возвращать napi_closing даже до того, как счётчик ссылок достигнет нуля. В частности, napi_call_threadsafe_function() вернёт napi_closing, тем самым сообщив нитям, что асинхронные вызовы к функции с защитой от множественных потоков больше невозможны. Это может служить критерием завершения нити. При получении возвращаемого значения napi_closing от napi_call_threadsafe_function() нить не должна больше использовать функцию с защитой от множественных потоков, поскольку она больше не гарантируется как выделенная.
Аналогично обработчикам libuv, функции с защитой от множественных потоков могут быть "ссылочные" и "нессылочные". Ссылочная функция с защитой от множественных потоков сохранит цикл событий в нити, в которой она создана, до тех пор, пока функция с защитой от множественных потоков не будет уничтожена. В отличие от этого, нессылочная функция с защитой от множественных потоков не предотвратит выход из цикла событий. Для этой цели существуют API napi_ref_threadsafe_function и napi_unref_threadsafe_function.
napi_create_threadsafe_function
NAPI_EXTERN napi_status
napi_create_threadsafe_function(napi_env env,
napi_value func,
napi_value async_resource,
napi_value async_resource_name,
size_t max_queue_size,
size_t initial_thread_count,
void* thread_finalize_data,
napi_finalize thread_finalize_cb,
void* context,
napi_threadsafe_function_call_js call_js_cb,
napi_threadsafe_function* result);
-
[in] env: Окружение, в котором вызывается API. -
[in] func: Необязательная функция JavaScript для вызова из другой нити. Она должна быть предоставлена, еслиNULLпередано вcall_js_cb. -
[in] async_resource: Необязательный объект, связанный с асинхронной работой, который будет передан возможнымasync_hooksinitхукам. -
[in] async_resource_name: Строка JavaScript, предоставляющая идентификатор типа ресурса, который предоставляется для диагностической информации, предоставляемой APIasync_hooks. -
[in] max_queue_size: Максимальный размер очереди.0для отсутствия ограничения. -
[in] initial_thread_count: Начальное количество нитей, включая главную нить, которые будут использовать эту функцию. -
[in] thread_finalize_data: Необязательные данные, передаваемые вthread_finalize_cb. -
[in] thread_finalize_cb: Необязательная функция для вызова при уничтоженииnapi_threadsafe_function. -
[in] context: Необязательные данные для прикрепления к результирующемуnapi_threadsafe_function. -
[in] call_js_cb: Необязательный обратный вызов, который вызывает функцию JavaScript в ответ на вызов в другой нити. Этот обратный вызов будет вызван в основной нити. Если он не задан, функция JavaScript будет вызвана без параметров и сundefinedкак значениемthis. -
[out] result: Асинхронная функция JavaScript с защитой от множественных потоков.
napi_get_threadsafe_function_context
NAPI_EXTERN napi_status
napi_get_threadsafe_function_context(napi_threadsafe_function func,
void** result);
-
[in] func: Функция с защитой от множественных потоков, для которой необходимо получить контекст. -
[out] result: Место для хранения контекста.
Этот API может быть вызван из любой нити, которая использует func.
napi_call_threadsafe_function
NAPI_EXTERN napi_status
napi_call_threadsafe_function(napi_threadsafe_function func,
void* data,
napi_threadsafe_function_call_mode is_blocking);
-
[in] func: Асинхронная функция JavaScript с защитой от множественных потоков для вызова. -
[in] data: Данные для отправки в JavaScript через обратный вызовcall_js_cb, предоставленный во время создания функции JavaScript с защитой от множественных потоков. -
[in] is_blocking: Флаг, значение которого может бытьnapi_tsfn_blockingдля указания того, что вызов должен заблокироваться, если очередь заполнена, илиnapi_tsfn_nonblockingдля указания того, что вызов должен вернуть результат немедленно со статусомnapi_queue_full, когда очередь заполнена.
Этот API вернёт napi_closing если napi_release_threadsafe_function() был вызван с abort , установленным в napi_tsfn_abort из любой нити. Значение добавляется в очередь только в том случае, если API возвращает napi_ok.
Этот API может быть вызван из любой нити, которая использует func.
napi_acquire_threadsafe_function
NAPI_EXTERN napi_status napi_acquire_threadsafe_function(napi_threadsafe_function func);
-
[in] func: Асинхронная функция JavaScript с защитой от множественных потоков, для которой необходимо начать использование.
Нить должна вызвать этот API перед передачей func в любой другой API с защитой от множественных потоков, чтобы указать, что она будет использовать func. Это предотвращает уничтожение func при остановке всех других нитей, использующих его.
Этот API может быть вызван из любой нити, которая начнёт использовать func.
napi_release_threadsafe_function
NAPI_EXTERN napi_status
napi_release_threadsafe_function(napi_threadsafe_function func,
napi_threadsafe_function_release_mode mode);
-
[in] func: Асинхронная функция JavaScript с защитой от множественных потоков, для которой необходимо уменьшить счётчик ссылок. -
[in] mode: Флаг, значение которого может бытьnapi_tsfn_releaseдля указания того, что текущая нить больше не будет выполнять вызовы функции с защитой от множественных потоков, илиnapi_tsfn_abortдля указания того, что помимо текущей нити ни одна другая нить не должна делать дальнейшие вызовы функции с защитой от множественных потоков. Если он установлен вnapi_tsfn_abort, дальнейшие вызовыnapi_call_threadsafe_function()вернутnapi_closing, и больше никаких значений не будут помещены в очередь.
Нить должна вызвать этот API, когда она перестаёт использовать func. Передача func в любой API с защитой от множественных потоков после вызова этого API приведёт к неопределённым результатам, так как func может быть уничтожен.
Этот API может быть вызван из любой нити, которая прекратит использование func.
napi_ref_threadsafe_function
NAPI_EXTERN napi_status napi_ref_threadsafe_function(napi_env env, napi_threadsafe_function func);
-
[in] env: Среда, в которой вызывается API. -
[in] func: Функция с защитой от одновременного доступа нескольких потоков, которую необходимо сослаться.
Этот API используется для указания того, что цикл событий, выполняющийся в главном потоке, не должен завершаться до тех пор, пока func не будет уничтожен. Подобно uv_ref, он также идемпотентен.
Этот API может вызываться только из главного потока.
napi_unref_threadsafe_function
NAPI_EXTERN napi_status napi_unref_threadsafe_function(napi_env env, napi_threadsafe_function func);
-
[in] env: Среда, в которой вызывается API. -
[in] func: Функция с защитой от одновременного доступа нескольких потоков, которую необходимо освободить от ссылок.
Этот API используется для указания того, что цикл событий, выполняющийся в главном потоке, может завершиться до того, как func будет уничтожен. Подобно uv_unref, он также идемпотентен.
Этот API может вызываться только из главного потока.
© Joyent, Inc. and other Node contributors
Licensed under the MIT License.
Node.js is a trademark of Joyent, Inc. and is used with its permission.
We are not endorsed by or affiliated with Joyent.
https://nodejs.org/dist/latest-v10.x/docs/api/n-api.html