From ebe485f0165f5ae46c19ce083c574fcd4181aedf Mon Sep 17 00:00:00 2001 From: Sam Cao Date: Tue, 30 May 2023 12:22:20 +0800 Subject: [PATCH] =?UTF-8?q?=F0=9F=8F=83=20Javet=20v2.2.0=20(#245)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Upgraded V8 to `v11.4.183.14` (2023-05-23) * Improved the performance of `V8FunctionCallback.receiveCallback()`, `IV8ValueObject.forEach()`, `IV8ValueMap.forEach()`, `IV8ValueArray.forEach()`, `IV8ValueArray.push()`, `IV8ValueObject.set()`, `IV8ValueMap.set()`, * Added `IV8ValueObject.batchGet()`, `IV8ValueMap.batchGet()`, `IV8ValueArray.batchGet()` * Added `JavetCallbackType`, `IJavetDirectCallable`, `IJavetDirectProxyHandler` to allow callback without reflection * Redesigned `IV8ValueObject.bindFunction()`, `IV8ValueObject.bindProperty()`, `IV8ValueObject.unbindFunction()`, `IV8ValueObject.unbindProperty()`, `JavetCallbackContext` * Renamed `JavetDynamicProxy*` to `JavetReflectionProxy*` * Added error code 408 CallbackTypeNotSupported * Created [JavetPerf](https://github.com/caoccao/JavetPerf) for tracking the performance among various Javet releases --- .github/workflows/linux_build_artifact.yml | 4 +- .../workflows/linux_build_node_v8_image.yml | 4 +- README.rst | 18 +- android/javet-android/build.gradle.kts | 2 +- .../src/main/AndroidManifest.xml | 2 +- android/pom.xml | 4 +- build.gradle.kts | 2 +- cpp/CMakeLists.txt | 10 +- cpp/build-android.sh | 2 +- cpp/build-linux.sh | 2 +- cpp/build-macos.sh | 2 +- cpp/build-windows.cmd | 2 +- .../com_caoccao_javet_interop_V8Native.cpp | 2171 -------------- cpp/jni/com_caoccao_javet_interop_V8Native.h | 870 ++++-- cpp/jni/javet_callbacks.cpp | 13 +- cpp/jni/javet_converter.cpp | 67 +- cpp/jni/javet_converter.h | 17 +- cpp/jni/javet_jni.h | 30 + cpp/jni/javet_jni_array.cpp | 57 + cpp/jni/javet_jni_array_buffer.cpp | 45 + cpp/jni/javet_jni_context.cpp | 81 + ...NodeNative.cpp => javet_jni_core_node.cpp} | 13 +- cpp/jni/javet_jni_core_v8.cpp | 449 +++ cpp/jni/javet_jni_function.cpp | 624 ++++ cpp/jni/javet_jni_map.cpp | 404 +++ cpp/jni/javet_jni_module.cpp | 174 ++ cpp/jni/javet_jni_object.cpp | 874 ++++++ cpp/jni/javet_jni_promise.cpp | 166 ++ cpp/jni/javet_jni_proxy.cpp | 75 + cpp/jni/javet_jni_script.cpp | 128 + cpp/jni/javet_jni_set.cpp | 91 + cpp/jni/javet_jni_symbol.cpp | 29 + cpp/jni/javet_resource_node.rc | 12 +- cpp/jni/javet_resource_v8.rc | 12 +- docker/android/base.Dockerfile | 4 +- docker/android/build.Dockerfile | 2 +- docker/linux-arm64/base_all_in_one.Dockerfile | 4 +- docker/linux-arm64/base_gradle.Dockerfile | 2 +- docker/linux-arm64/base_v8.Dockerfile | 6 +- docker/linux-arm64/build_artifact.Dockerfile | 4 +- .../linux-x86_64/base_all_in_one.Dockerfile | 4 +- docker/linux-x86_64/base_gradle.Dockerfile | 2 +- docker/linux-x86_64/base_v8.Dockerfile | 6 +- .../linux-x86_64/build_all_in_one.Dockerfile | 2 +- docker/linux-x86_64/build_artifact.Dockerfile | 4 +- docker/windows-x86_64/base.Dockerfile | 4 +- docker/windows-x86_64/build.Dockerfile | 2 +- docs/_static/documentation_options.js | 2 +- docs/conf.py | 2 +- docs/development/build.html | 9 +- .../development/build_javet_from_scratch.html | 9 +- docs/development/build_javet_with_docker.html | 9 +- .../build_javet_with_pre_built_binaries.html | 9 +- .../debug_with_chrome_developer_tools.html | 15 +- docs/development/design.html | 15 +- docs/development/index.html | 10 +- docs/development/index.rst | 1 + docs/development/performance.html | 345 +++ docs/development/performance.rst | 5 + docs/development/test.html | 9 +- docs/development/tools.html | 9 +- docs/faq/background/history_with_j2v8.html | 9 +- docs/faq/background/index.html | 9 +- .../background/what_is_the_motivation.html | 9 +- .../development/how_to_think_in_javet.html | 9 +- docs/faq/development/index.html | 9 +- .../where_are_es6_api_in_v8_mode.html | 9 +- .../development/where_are_the_examples.html | 9 +- ...he_inspector_disabled_in_node_js_mode.html | 9 +- .../can_javet_support_legacy_linux.html | 9 +- .../environment/can_javet_support_mac.html | 9 +- docs/faq/environment/index.html | 9 +- docs/faq/index.html | 15 +- ...ary_dll_initialization_routine_failed.html | 9 +- .../can_i18n_be_supported.html | 9 +- ...can_i_debug_javet_in_chrome_dev_tools.html | 9 +- docs/faq/troubleshooting/index.html | 9 +- ...why_node_js_crashes_when_being_closed.html | 9 +- docs/genindex.html | 9 +- docs/index.html | 30 +- .../converters/bridge_converter.html | 9 +- .../converters/custom_converter.html | 9 +- docs/reference/converters/index.html | 9 +- .../converters/object_converter.html | 9 +- .../converters/primitive_converter.html | 9 +- .../reference/converters/proxy_converter.html | 9 +- docs/reference/index.html | 9 +- docs/reference/javadoc/allclasses-frame.html | 35 +- .../reference/javadoc/allclasses-noframe.html | 35 +- .../javet/annotations/CheckReturnValue.html | 4 +- .../caoccao/javet/annotations/NodeModule.html | 4 +- .../caoccao/javet/annotations/V8Allow.html | 4 +- .../javet/annotations/V8BindingEnabler.html | 4 +- .../caoccao/javet/annotations/V8Block.html | 4 +- .../caoccao/javet/annotations/V8Convert.html | 15 +- .../caoccao/javet/annotations/V8Function.html | 4 +- .../caoccao/javet/annotations/V8Getter.html | 4 +- .../caoccao/javet/annotations/V8Property.html | 4 +- .../annotations/V8ProxyFunctionApply.html | 4 +- .../javet/annotations/V8RuntimeSetter.html | 4 +- .../caoccao/javet/annotations/V8Setter.html | 4 +- .../javet/annotations/package-frame.html | 2 +- .../javet/annotations/package-summary.html | 4 +- .../javet/annotations/package-tree.html | 16 +- .../javet/entities/JavetEntityFunction.html | 4 +- .../javet/entities/JavetEntityMap.html | 4 +- .../javet/entities/JavetEntitySymbol.html | 4 +- .../caoccao/javet/entities/package-frame.html | 2 +- .../javet/entities/package-summary.html | 4 +- .../caoccao/javet/entities/package-tree.html | 4 +- .../caoccao/javet/enums/JSFunctionType.html | 4 +- .../caoccao/javet/enums/JSRuntimeType.html | 4 +- .../com/caoccao/javet/enums/JSScopeType.html | 4 +- .../caoccao/javet/enums/JavetErrorType.html | 4 +- .../javet/enums/JavetPromiseRejectEvent.html | 4 +- .../javet/enums/V8AllocationSpace.html | 4 +- .../com/caoccao/javet/enums/V8AwaitMode.html | 4 +- .../caoccao/javet/enums/V8ContextType.html | 4 +- .../caoccao/javet/enums/V8ConversionMode.html | 4 +- .../javet/enums/V8GCCallbackFlags.html | 4 +- .../com/caoccao/javet/enums/V8GCType.html | 4 +- .../com/caoccao/javet/enums/V8ProxyMode.html | 4 +- .../com/caoccao/javet/enums/V8ScopeType.html | 4 +- .../javet/enums/V8ValueInternalType.html | 4 +- .../javet/enums/V8ValueReferenceType.html | 4 +- .../javet/enums/V8ValueSymbolType.html | 4 +- .../caoccao/javet/enums/package-frame.html | 2 +- .../caoccao/javet/enums/package-summary.html | 4 +- .../com/caoccao/javet/enums/package-tree.html | 26 +- .../BaseJavetScriptingException.html | 4 +- .../exceptions/JavetCompilationException.html | 4 +- .../exceptions/JavetConverterException.html | 4 +- .../caoccao/javet/exceptions/JavetError.html | 326 ++- .../javet/exceptions/JavetException.html | 4 +- .../exceptions/JavetExecutionException.html | 4 +- .../exceptions/JavetOutOfMemoryException.html | 4 +- .../javet/exceptions/JavetScriptingError.html | 4 +- .../exceptions/JavetTerminatedException.html | 4 +- .../javet/exceptions/package-frame.html | 2 +- .../javet/exceptions/package-summary.html | 4 +- .../javet/exceptions/package-tree.html | 4 +- .../interception/BaseJavetInterceptor.html | 4 +- .../logging/BaseJavetConsoleInterceptor.html | 4 +- .../JavetStandardConsoleInterceptor.html | 4 +- .../interception/logging/package-frame.html | 2 +- .../interception/logging/package-summary.html | 4 +- .../interception/logging/package-tree.html | 4 +- .../javet/interception/package-frame.html | 2 +- .../javet/interception/package-summary.html | 4 +- .../javet/interception/package-tree.html | 4 +- .../caoccao/javet/interfaces/IEnumBitset.html | 4 +- .../javet/interfaces/IJavaFunction.html | 4 +- .../javet/interfaces/IJavaSupplier.html | 4 +- .../javet/interfaces/IJavetAnonymous.html | 4 +- .../javet/interfaces/IJavetBiConsumer.html | 15 +- .../javet/interfaces/IJavetBiFunction.html | 257 ++ .../interfaces/IJavetBiIndexedConsumer.html | 33 +- .../javet/interfaces/IJavetClosable.html | 8 +- .../interfaces/IJavetEntityFunction.html | 4 +- .../javet/interfaces/IJavetEntityMap.html | 4 +- .../javet/interfaces/IJavetInterceptor.html | 4 +- .../javet/interfaces/IJavetLogger.html | 4 +- .../javet/interfaces/IJavetMappable.html | 4 +- .../javet/interfaces/IJavetResettable.html | 4 +- .../javet/interfaces/IJavetSupplier.html | 4 +- .../javet/interfaces/IJavetUniConsumer.html | 15 +- .../javet/interfaces/IJavetUniFunction.html | 253 ++ .../interfaces/IJavetUniIndexedConsumer.html | 15 +- .../javet/interfaces/IV8ModuleResolver.html | 4 +- .../javet/interfaces/package-frame.html | 4 +- .../javet/interfaces/package-summary.html | 36 +- .../javet/interfaces/package-tree.html | 8 +- .../caoccao/javet/interop/INodeNative.html | 6 +- .../caoccao/javet/interop/IV8Cloneable.html | 6 +- .../caoccao/javet/interop/IV8Convertible.html | 4 +- .../caoccao/javet/interop/IV8Creatable.html | 4 +- .../caoccao/javet/interop/IV8Executable.html | 4 +- .../javet/interop/IV8InspectorListener.html | 4 +- .../com/caoccao/javet/interop/IV8Native.html | 2502 +++++++++++------ .../caoccao/javet/interop/NodeRuntime.html | 13 +- .../com/caoccao/javet/interop/V8Host.html | 4 +- .../caoccao/javet/interop/V8Inspector.html | 4 +- .../com/caoccao/javet/interop/V8Internal.html | 1567 ++++++++--- .../com/caoccao/javet/interop/V8Locker.html | 4 +- .../com/caoccao/javet/interop/V8Notifier.html | 4 +- .../com/caoccao/javet/interop/V8Runtime.html | 393 ++- .../com/caoccao/javet/interop/V8Scope.html | 4 +- .../caoccao/javet/interop/V8ScriptOrigin.html | 4 +- .../javet/interop/binding/BindingContext.html | 4 +- .../interop/binding/ClassDescriptor.html | 4 +- .../interop/binding/MethodDescriptor.html | 4 +- .../javet/interop/binding/package-frame.html | 2 +- .../interop/binding/package-summary.html | 4 +- .../javet/interop/binding/package-tree.html | 4 +- .../IJavetDirectCallable.DirectCall.html | 182 ++ .../IJavetDirectCallable.GetterAndNoThis.html | 250 ++ .../IJavetDirectCallable.GetterAndThis.html | 252 ++ ...JavetDirectCallable.NoThisAndNoResult.html | 247 ++ .../IJavetDirectCallable.NoThisAndResult.html | 250 ++ .../IJavetDirectCallable.SetterAndNoThis.html | 252 ++ .../IJavetDirectCallable.SetterAndThis.html | 255 ++ .../IJavetDirectCallable.ThisAndNoResult.html | 250 ++ .../IJavetDirectCallable.ThisAndResult.html | 256 ++ .../callback/IJavetDirectCallable.html | 333 +++ .../interop/callback/IJavetGCCallback.html | 8 +- .../callback/IJavetPromiseRejectCallback.html | 4 +- .../callback/JavetCallbackContext.html | 283 +- .../interop/callback/JavetCallbackType.html | 559 ++++ .../interop/callback/JavetGCCallback.html | 8 +- .../callback/JavetPromiseRejectCallback.html | 4 +- .../interop/callback/V8FunctionCallback.html | 16 +- .../javet/interop/callback/package-frame.html | 16 +- .../interop/callback/package-summary.html | 87 +- .../javet/interop/callback/package-tree.html | 33 +- .../converters/BaseJavetConverter.html | 4 +- .../interop/converters/IJavetConverter.html | 4 +- .../converters/JavetBridgeConverter.html | 4 +- .../converters/JavetConverterConfig.html | 128 +- .../converters/JavetObjectConverter.html | 4 +- .../converters/JavetPrimitiveConverter.html | 4 +- .../converters/JavetProxyConverter.html | 4 +- .../interop/converters/package-frame.html | 2 +- .../interop/converters/package-summary.html | 4 +- .../interop/converters/package-tree.html | 4 +- .../javet/interop/engine/IJavetEngine.html | 4 +- .../interop/engine/IJavetEngineGuard.html | 4 +- .../interop/engine/IJavetEnginePool.html | 4 +- .../javet/interop/engine/JavetEngine.html | 4 +- .../interop/engine/JavetEngineConfig.html | 4 +- .../interop/engine/JavetEngineGuard.html | 4 +- .../javet/interop/engine/JavetEnginePool.html | 4 +- .../interop/engine/JavetEngineUsage.html | 4 +- .../engine/observers/IV8RuntimeObserver.html | 4 +- ...meObserverAverageCallbackContextCount.html | 4 +- ...8RuntimeObserverAverageReferenceCount.html | 4 +- ...eObserverAverageV8HeapSpaceStatistics.html | 4 +- ...untimeObserverAverageV8HeapStatistics.html | 4 +- ...V8RuntimeObserverAverageV8ModuleCount.html | 4 +- .../engine/observers/package-frame.html | 2 +- .../engine/observers/package-summary.html | 4 +- .../engine/observers/package-tree.html | 4 +- .../javet/interop/engine/package-frame.html | 2 +- .../javet/interop/engine/package-summary.html | 4 +- .../javet/interop/engine/package-tree.html | 4 +- .../interop/executors/BaseV8Executor.html | 4 +- .../javet/interop/executors/IV8Executor.html | 4 +- .../interop/executors/V8FileExecutor.html | 4 +- .../interop/executors/V8PathExecutor.html | 4 +- .../interop/executors/V8StringExecutor.html | 4 +- .../interop/executors/package-frame.html | 2 +- .../interop/executors/package-summary.html | 4 +- .../javet/interop/executors/package-tree.html | 4 +- .../loader/IJavetLibLoadingListener.html | 4 +- .../javet/interop/loader/JavetLibLoader.html | 4 +- .../loader/JavetLibLoadingListener.html | 4 +- .../javet/interop/loader/package-frame.html | 2 +- .../javet/interop/loader/package-summary.html | 4 +- .../javet/interop/loader/package-tree.html | 4 +- .../monitoring/V8HeapSpaceStatistics.html | 4 +- .../interop/monitoring/V8HeapStatistics.html | 4 +- .../monitoring/V8SharedMemoryStatistics.html | 4 +- .../interop/monitoring/package-frame.html | 2 +- .../interop/monitoring/package-summary.html | 4 +- .../interop/monitoring/package-tree.html | 4 +- .../interop/options/NodeRuntimeOptions.html | 8 +- .../javet/interop/options/RuntimeOptions.html | 48 +- .../javet/interop/options/V8Flags.html | 4 +- .../interop/options/V8RuntimeOptions.html | 8 +- .../javet/interop/options/package-frame.html | 2 +- .../interop/options/package-summary.html | 4 +- .../javet/interop/options/package-tree.html | 4 +- .../caoccao/javet/interop/package-frame.html | 2 +- .../javet/interop/package-summary.html | 4 +- .../caoccao/javet/interop/package-tree.html | 4 +- .../proxy/BaseJavetDirectProxyHandler.html | 329 +++ .../interop/proxy/BaseJavetProxyHandler.html | 739 +---- .../proxy/BaseJavetProxySymbolConverter.html | 8 +- .../BaseJavetReflectionProxyHandler.html | 1005 +++++++ .../proxy/IJavetDirectProxyHandler.html | 580 ++++ .../interop/proxy/IJavetProxyHandler.html | 412 ++- .../proxy/IJavetProxySymbolConverter.html | 8 +- ...tml => IJavetReflectionObjectFactory.html} | 38 +- .../JavetDirectProxyFunctionHandler.html | 423 +++ .../proxy/JavetDirectProxyObjectHandler.html | 510 ++++ .../proxy/JavetDynamicProxyClassHandler.html | 604 ---- .../JavetDynamicProxyFunctionHandler.html | 408 --- .../JavetProxySymbolIterableConverter.html | 8 +- .../JavetProxySymbolToPrimitiveConverter.html | 8 +- .../JavetReflectionProxyClassHandler.html | 668 +++++ ....html => JavetReflectionProxyFactory.html} | 52 +- .../JavetReflectionProxyFunctionHandler.html | 481 ++++ ...=> JavetReflectionProxyObjectHandler.html} | 236 +- ...roxyV8ValueFunctionInvocationHandler.html} | 46 +- ...nProxyV8ValueObjectInvocationHandler.html} | 46 +- .../javet/interop/proxy/package-frame.html | 21 +- .../javet/interop/proxy/package-summary.html | 80 +- .../javet/interop/proxy/package-tree.html | 36 +- .../javet/node/modules/BaseNodeModule.html | 4 +- .../javet/node/modules/INodeModule.html | 4 +- .../javet/node/modules/NodeModuleAny.html | 4 +- .../javet/node/modules/NodeModuleModule.html | 4 +- .../javet/node/modules/NodeModuleProcess.html | 4 +- .../javet/node/modules/package-frame.html | 2 +- .../javet/node/modules/package-summary.html | 4 +- .../javet/node/modules/package-tree.html | 4 +- .../javet/utils/JavetDateTimeUtils.html | 4 +- .../javet/utils/JavetDefaultLogger.html | 4 +- .../com/caoccao/javet/utils/JavetOSUtils.html | 4 +- .../javet/utils/JavetReflectionUtils.html | 4 +- .../javet/utils/JavetResourceUtils.html | 28 +- .../caoccao/javet/utils/JavetStringUtils.html | 4 +- .../caoccao/javet/utils/JavetTypeUtils.html | 4 +- .../javet/utils/JavetVirtualObject.html | 4 +- .../javet/utils/SimpleFreeMarkerFormat.html | 4 +- .../com/caoccao/javet/utils/SimpleMap.html | 4 +- .../javet/utils/ThreadSafeMap.Type.html | 4 +- .../caoccao/javet/utils/ThreadSafeMap.html | 4 +- .../com/caoccao/javet/utils/V8ValueUtils.html | 4 +- .../caoccao/javet/utils/package-frame.html | 2 +- .../caoccao/javet/utils/package-summary.html | 4 +- .../com/caoccao/javet/utils/package-tree.html | 4 +- .../receivers/IJavetCallbackReceiver.html | 4 +- .../receivers/JavetCallbackReceiver.html | 4 +- .../javet/utils/receivers/package-frame.html | 2 +- .../utils/receivers/package-summary.html | 4 +- .../javet/utils/receivers/package-tree.html | 4 +- .../com/caoccao/javet/values/IV8Value.html | 6 +- .../com/caoccao/javet/values/V8Data.html | 4 +- .../com/caoccao/javet/values/V8Value.html | 4 +- .../caoccao/javet/values/package-frame.html | 2 +- .../caoccao/javet/values/package-summary.html | 4 +- .../caoccao/javet/values/package-tree.html | 4 +- .../values/primitive/V8ValueBigInteger.html | 4 +- .../values/primitive/V8ValueBoolean.html | 4 +- .../javet/values/primitive/V8ValueDouble.html | 4 +- .../values/primitive/V8ValueInteger.html | 4 +- .../javet/values/primitive/V8ValueLong.html | 4 +- .../javet/values/primitive/V8ValueNull.html | 4 +- .../values/primitive/V8ValuePrimitive.html | 4 +- .../javet/values/primitive/V8ValueString.html | 4 +- .../values/primitive/V8ValueUndefined.html | 4 +- .../values/primitive/V8ValueUnknown.html | 4 +- .../primitive/V8ValueZonedDateTime.html | 4 +- .../javet/values/primitive/package-frame.html | 2 +- .../values/primitive/package-summary.html | 4 +- .../javet/values/primitive/package-tree.html | 4 +- .../javet/values/reference/IV8Cacheable.html | 276 ++ .../javet/values/reference/IV8Context.html | 8 +- .../javet/values/reference/IV8Module.html | 49 +- .../javet/values/reference/IV8Script.html | 41 +- .../javet/values/reference/IV8ValueArray.html | 202 +- ...IV8ValueFunction.GetScopeInfosOptions.html | 4 +- .../reference/IV8ValueFunction.ScopeInfo.html | 4 +- .../IV8ValueFunction.ScopeInfos.html | 4 +- .../IV8ValueFunction.ScriptSource.html | 4 +- ...IV8ValueFunction.SetSourceCodeOptions.html | 4 +- .../values/reference/IV8ValueFunction.html | 91 +- .../values/reference/IV8ValueIterator.html | 4 +- .../reference/IV8ValueKeyContainer.html | 21 +- .../javet/values/reference/IV8ValueMap.html | 21 +- .../values/reference/IV8ValueObject.html | 749 +++-- .../reference/IV8ValuePromise.IListener.html | 4 +- .../values/reference/IV8ValuePromise.html | 13 +- .../javet/values/reference/IV8ValueProxy.html | 21 +- .../values/reference/IV8ValueReference.html | 6 +- .../javet/values/reference/IV8ValueSet.html | 21 +- .../values/reference/IV8ValueTypedArray.html | 21 +- .../javet/values/reference/V8Context.html | 4 +- .../javet/values/reference/V8Module.html | 18 +- .../javet/values/reference/V8Script.html | 18 +- .../values/reference/V8ValueArguments.html | 21 +- .../javet/values/reference/V8ValueArray.html | 164 +- .../values/reference/V8ValueArrayBuffer.html | 17 +- .../values/reference/V8ValueDataView.html | 17 +- .../javet/values/reference/V8ValueError.html | 17 +- .../values/reference/V8ValueFunction.html | 27 +- .../values/reference/V8ValueGlobalObject.html | 17 +- .../values/reference/V8ValueIterator.html | 17 +- .../javet/values/reference/V8ValueMap.html | 577 +++- .../javet/values/reference/V8ValueObject.html | 751 ++++- .../values/reference/V8ValuePromise.html | 17 +- .../javet/values/reference/V8ValueProxy.html | 17 +- .../values/reference/V8ValueReference.html | 4 +- .../javet/values/reference/V8ValueRegExp.html | 17 +- .../javet/values/reference/V8ValueSet.html | 95 +- .../reference/V8ValueSharedArrayBuffer.html | 17 +- .../javet/values/reference/V8ValueSymbol.html | 17 +- .../values/reference/V8ValueSymbolObject.html | 17 +- .../values/reference/V8ValueTypedArray.html | 79 +- .../values/reference/V8ValueWeakMap.html | 17 +- .../values/reference/V8ValueWeakSet.html | 17 +- .../reference/builtin/V8ValueBuiltInJson.html | 17 +- .../builtin/V8ValueBuiltInObject.html | 17 +- .../builtin/V8ValueBuiltInPromise.html | 19 +- .../builtin/V8ValueBuiltInSymbol.html | 19 +- .../reference/builtin/package-frame.html | 2 +- .../reference/builtin/package-summary.html | 4 +- .../reference/builtin/package-tree.html | 4 +- .../javet/values/reference/package-frame.html | 3 +- .../values/reference/package-summary.html | 46 +- .../javet/values/reference/package-tree.html | 34 +- .../javet/values/virtual/V8VirtualValue.html | 4 +- .../values/virtual/V8VirtualValueList.html | 4 +- .../javet/values/virtual/package-frame.html | 2 +- .../javet/values/virtual/package-summary.html | 4 +- .../javet/values/virtual/package-tree.html | 4 +- docs/reference/javadoc/constant-values.html | 291 +- docs/reference/javadoc/deprecated-list.html | 4 +- docs/reference/javadoc/help-doc.html | 4 +- docs/reference/javadoc/index-all.html | 1277 ++++++--- docs/reference/javadoc/index.html | 2 +- docs/reference/javadoc/overview-frame.html | 2 +- docs/reference/javadoc/overview-summary.html | 8 +- docs/reference/javadoc/overview-tree.html | 178 +- docs/reference/javadoc/serialized-form.html | 7 +- docs/reference/resource_management/index.html | 9 +- .../resource_management/load_and_unload.html | 9 +- docs/reference/resource_management/lock.html | 9 +- .../memory_management.html | 9 +- .../resource_management/modularization.html | 9 +- .../resource_management/performance.html | 9 +- docs/reference/tips/best_practices.html | 9 +- docs/reference/tips/index.html | 9 +- docs/reference/todo_list.html | 9 +- .../troubleshooting/error_codes.html | 46 +- .../reference/troubleshooting/error_codes.rst | 1 + docs/reference/troubleshooting/index.html | 9 +- docs/reference/troubleshooting/logging.html | 9 +- .../troubleshooting/termination.html | 9 +- docs/reference/v8_values/index.html | 9 +- docs/reference/v8_values/v8_collection.html | 9 +- docs/reference/v8_values/v8_function.html | 9 +- docs/reference/v8_values/v8_promise.html | 9 +- docs/release_notes/index.html | 18 +- docs/release_notes/index.rst | 3 +- docs/release_notes/release_notes_0_7.html | 9 +- docs/release_notes/release_notes_0_8.html | 9 +- docs/release_notes/release_notes_0_9.html | 9 +- docs/release_notes/release_notes_1_0.html | 9 +- docs/release_notes/release_notes_1_1.html | 9 +- docs/release_notes/release_notes_2_0.html | 9 +- docs/release_notes/release_notes_2_1.html | 41 +- docs/release_notes/release_notes_2_1.rst | 2 +- docs/release_notes/release_notes_2_2.html | 376 +++ docs/release_notes/release_notes_2_2.rst | 15 + docs/search.html | 9 +- docs/searchindex.js | 2 +- docs/tutorial/advanced/index.html | 9 +- .../advanced/interact_with_node_js.html | 9 +- .../advanced/java_and_javascript_interop.html | 9 +- docs/tutorial/advanced/object_converter.html | 9 +- docs/tutorial/basic/engine_pool.html | 9 +- docs/tutorial/basic/hello_javet.html | 9 +- docs/tutorial/basic/index.html | 9 +- docs/tutorial/basic/installation.html | 25 +- docs/tutorial/basic/installation.rst | 16 +- docs/tutorial/basic/interception.html | 9 +- docs/tutorial/basic/javet_shell.html | 9 +- .../basic/node_js_mode_and_v8_mode.html | 9 +- docs/tutorial/basic/polyfill.html | 9 +- docs/tutorial/basic/spring_integration.html | 9 +- docs/tutorial/index.html | 9 +- docs/tutorial/migration_guides/index.html | 9 +- .../migration_guides/migrate_from_j2v8.html | 9 +- pom.xml | 4 +- scripts/node/javet-rebuild/rebuild.cmd | 2 +- scripts/node/javet-rebuild/rebuild.sh | 2 +- scripts/python/change_javet_version.py | 2 +- scripts/python/change_node_v8_version.py | 2 +- .../caoccao/javet/annotations/V8Convert.java | 6 + .../caoccao/javet/enums/JSRuntimeType.java | 2 +- .../caoccao/javet/exceptions/JavetError.java | 119 +- .../logging/BaseJavetConsoleInterceptor.java | 6 +- .../javet/interfaces/IJavetBiConsumer.java | 1 + .../javet/interfaces/IJavetBiFunction.java | 43 + .../interfaces/IJavetBiIndexedConsumer.java | 11 +- .../javet/interfaces/IJavetUniConsumer.java | 1 + .../javet/interfaces/IJavetUniFunction.java | 41 + .../interfaces/IJavetUniIndexedConsumer.java | 1 + .../com/caoccao/javet/interop/IV8Native.java | 242 +- .../com/caoccao/javet/interop/V8Internal.java | 383 ++- .../com/caoccao/javet/interop/V8Native.java | 325 ++- .../com/caoccao/javet/interop/V8Runtime.java | 1749 ++++++++---- .../callback/IJavetDirectCallable.java | 211 ++ .../callback/JavetCallbackContext.java | 190 +- .../interop/callback/JavetCallbackType.java | 124 + .../interop/callback/V8FunctionCallback.java | 185 +- .../converters/JavetConverterConfig.java | 47 +- .../converters/JavetObjectConverter.java | 149 +- .../converters/JavetProxyConverter.java | 29 +- .../javet/interop/loader/JavetLibLoader.java | 2 +- .../javet/interop/options/RuntimeOptions.java | 24 +- .../proxy/BaseJavetDirectProxyHandler.java | 41 + .../interop/proxy/BaseJavetProxyHandler.java | 811 +----- .../proxy/BaseJavetProxySymbolConverter.java | 21 +- .../BaseJavetReflectionProxyHandler.java | 706 +++++ .../proxy/IJavetDirectProxyHandler.java | 295 ++ .../interop/proxy/IJavetProxyHandler.java | 175 +- ...ava => IJavetReflectionObjectFactory.java} | 8 +- .../JavetDirectProxyFunctionHandler.java | 71 + .../proxy/JavetDirectProxyObjectHandler.java | 89 + .../JavetProxySymbolToPrimitiveConverter.java | 2 +- ... => JavetReflectionProxyClassHandler.java} | 57 +- ....java => JavetReflectionProxyFactory.java} | 30 +- ... JavetReflectionProxyFunctionHandler.java} | 52 +- ...a => JavetReflectionProxyInterceptor.java} | 27 +- ...=> JavetReflectionProxyObjectHandler.java} | 50 +- ...roxyV8ValueFunctionInvocationHandler.java} | 8 +- ...nProxyV8ValueObjectInvocationHandler.java} | 8 +- .../javet/interop/proxy/ScoredExecutable.java | 52 +- .../javet/interop/proxy/package-info.java | 2 +- .../javet/utils/JavetResourceUtils.java | 12 + .../javet/values/reference/IV8Cacheable.java | 35 + .../javet/values/reference/IV8Module.java | 4 +- .../javet/values/reference/IV8Script.java | 4 +- .../javet/values/reference/IV8ValueArray.java | 86 +- .../values/reference/IV8ValueFunction.java | 11 +- .../values/reference/IV8ValueObject.java | 349 ++- .../javet/values/reference/V8Module.java | 2 +- .../javet/values/reference/V8Script.java | 2 +- .../javet/values/reference/V8ValueArray.java | 81 +- .../values/reference/V8ValueFunction.java | 16 +- .../javet/values/reference/V8ValueMap.java | 169 +- .../javet/values/reference/V8ValueObject.java | 751 +++-- .../values/reference/V8ValuePromise.java | 12 +- .../javet/values/reference/V8ValueSet.java | 20 +- .../values/reference/V8ValueTypedArray.java | 13 +- .../values/reference/V8ValueWeakMap.java | 2 +- .../callback/TestV8FunctionCallback.java | 63 + .../converters/TestJavetObjectConverter.java | 26 +- .../TestJavetPrimitiveConverter.java | 18 +- .../converters/TestJavetProxyConverter.java | 165 +- ...e.java => TestJavetEnginePerformance.java} | 2 +- ...java => JavetReflectionObjectFactory.java} | 8 +- .../mock/MockDirectProxyFunctionHandler.java | 43 + .../mock/MockDirectProxyObjectHandler.java | 150 + .../values/reference/TestV8ValueArray.java | 61 +- .../values/reference/TestV8ValueFunction.java | 437 ++- .../values/reference/TestV8ValueMap.java | 45 +- .../values/reference/TestV8ValueObject.java | 101 +- .../values/reference/TestV8ValuePromise.java | 10 +- .../values/reference/TestV8ValueProxy.java | 162 +- 542 files changed, 28982 insertions(+), 10701 deletions(-) delete mode 100644 cpp/jni/com_caoccao_javet_interop_V8Native.cpp create mode 100644 cpp/jni/javet_jni.h create mode 100644 cpp/jni/javet_jni_array.cpp create mode 100644 cpp/jni/javet_jni_array_buffer.cpp create mode 100644 cpp/jni/javet_jni_context.cpp rename cpp/jni/{com_caoccao_javet_interop_NodeNative.cpp => javet_jni_core_node.cpp} (83%) create mode 100644 cpp/jni/javet_jni_core_v8.cpp create mode 100644 cpp/jni/javet_jni_function.cpp create mode 100644 cpp/jni/javet_jni_map.cpp create mode 100644 cpp/jni/javet_jni_module.cpp create mode 100644 cpp/jni/javet_jni_object.cpp create mode 100644 cpp/jni/javet_jni_promise.cpp create mode 100644 cpp/jni/javet_jni_proxy.cpp create mode 100644 cpp/jni/javet_jni_script.cpp create mode 100644 cpp/jni/javet_jni_set.cpp create mode 100644 cpp/jni/javet_jni_symbol.cpp create mode 100644 docs/development/performance.html create mode 100644 docs/development/performance.rst create mode 100644 docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetBiFunction.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetUniFunction.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.DirectCall.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.GetterAndNoThis.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.GetterAndThis.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.NoThisAndNoResult.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.NoThisAndResult.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.SetterAndNoThis.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.SetterAndThis.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.ThisAndNoResult.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.ThisAndResult.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/callback/JavetCallbackType.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/proxy/BaseJavetDirectProxyHandler.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/proxy/BaseJavetReflectionProxyHandler.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/proxy/IJavetDirectProxyHandler.html rename docs/reference/javadoc/com/caoccao/javet/interop/proxy/{IJavetDynamicObjectFactory.html => IJavetReflectionObjectFactory.html} (77%) create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDirectProxyFunctionHandler.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDirectProxyObjectHandler.html delete mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyClassHandler.html delete mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyFunctionHandler.html create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetReflectionProxyClassHandler.html rename docs/reference/javadoc/com/caoccao/javet/interop/proxy/{JavetDynamicProxyFactory.html => JavetReflectionProxyFactory.html} (77%) create mode 100644 docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetReflectionProxyFunctionHandler.html rename docs/reference/javadoc/com/caoccao/javet/interop/proxy/{JavetDynamicProxyObjectHandler.html => JavetReflectionProxyObjectHandler.html} (51%) rename docs/reference/javadoc/com/caoccao/javet/interop/proxy/{JavetDynamicProxyV8ValueFunctionInvocationHandler.html => JavetReflectionProxyV8ValueFunctionInvocationHandler.html} (75%) rename docs/reference/javadoc/com/caoccao/javet/interop/proxy/{JavetDynamicProxyV8ValueObjectInvocationHandler.html => JavetReflectionProxyV8ValueObjectInvocationHandler.html} (75%) create mode 100644 docs/reference/javadoc/com/caoccao/javet/values/reference/IV8Cacheable.html create mode 100644 docs/release_notes/release_notes_2_2.html create mode 100644 docs/release_notes/release_notes_2_2.rst create mode 100644 src/main/java/com/caoccao/javet/interfaces/IJavetBiFunction.java create mode 100644 src/main/java/com/caoccao/javet/interfaces/IJavetUniFunction.java create mode 100644 src/main/java/com/caoccao/javet/interop/callback/IJavetDirectCallable.java create mode 100644 src/main/java/com/caoccao/javet/interop/callback/JavetCallbackType.java create mode 100644 src/main/java/com/caoccao/javet/interop/proxy/BaseJavetDirectProxyHandler.java create mode 100644 src/main/java/com/caoccao/javet/interop/proxy/BaseJavetReflectionProxyHandler.java create mode 100644 src/main/java/com/caoccao/javet/interop/proxy/IJavetDirectProxyHandler.java rename src/main/java/com/caoccao/javet/interop/proxy/{IJavetDynamicObjectFactory.java => IJavetReflectionObjectFactory.java} (88%) create mode 100644 src/main/java/com/caoccao/javet/interop/proxy/JavetDirectProxyFunctionHandler.java create mode 100644 src/main/java/com/caoccao/javet/interop/proxy/JavetDirectProxyObjectHandler.java rename src/main/java/com/caoccao/javet/interop/proxy/{JavetDynamicProxyClassHandler.java => JavetReflectionProxyClassHandler.java} (69%) rename src/main/java/com/caoccao/javet/interop/proxy/{JavetDynamicProxyFactory.java => JavetReflectionProxyFactory.java} (71%) rename src/main/java/com/caoccao/javet/interop/proxy/{JavetDynamicProxyFunctionHandler.java => JavetReflectionProxyFunctionHandler.java} (50%) rename src/main/java/com/caoccao/javet/interop/proxy/{JavetDynamicProxyInterceptor.java => JavetReflectionProxyInterceptor.java} (83%) rename src/main/java/com/caoccao/javet/interop/proxy/{JavetDynamicProxyObjectHandler.java => JavetReflectionProxyObjectHandler.java} (85%) rename src/main/java/com/caoccao/javet/interop/proxy/{JavetDynamicProxyV8ValueFunctionInvocationHandler.java => JavetReflectionProxyV8ValueFunctionInvocationHandler.java} (84%) rename src/main/java/com/caoccao/javet/interop/proxy/{JavetDynamicProxyV8ValueObjectInvocationHandler.java => JavetReflectionProxyV8ValueObjectInvocationHandler.java} (86%) create mode 100644 src/main/java/com/caoccao/javet/values/reference/IV8Cacheable.java create mode 100644 src/test/java/com/caoccao/javet/interop/callback/TestV8FunctionCallback.java rename src/test/java/com/caoccao/javet/interop/engine/{TestPerformance.java => TestJavetEnginePerformance.java} (99%) rename src/test/java/com/caoccao/javet/interop/proxy/{JavetDynamicObjectFactory.java => JavetReflectionObjectFactory.java} (94%) create mode 100644 src/test/java/com/caoccao/javet/mock/MockDirectProxyFunctionHandler.java create mode 100644 src/test/java/com/caoccao/javet/mock/MockDirectProxyObjectHandler.java diff --git a/.github/workflows/linux_build_artifact.yml b/.github/workflows/linux_build_artifact.yml index d025802c2..da748a578 100644 --- a/.github/workflows/linux_build_artifact.yml +++ b/.github/workflows/linux_build_artifact.yml @@ -18,8 +18,8 @@ env: DOCKERHUB_USERNAME: ${{ secrets.DOCKERHUB_USERNAME }} DOCKERHUB_REPO_JAVET: ${{ secrets.DOCKERHUB_REPO_JAVET }} JAVET_NODE_VERSION: 18.16.0 - JAVET_V8_VERSION: 11.3.244.8 - JAVET_VERSION: 2.1.2 + JAVET_V8_VERSION: 11.4.183.14 + JAVET_VERSION: 2.2.0 jobs: javet_linux_x86_64: diff --git a/.github/workflows/linux_build_node_v8_image.yml b/.github/workflows/linux_build_node_v8_image.yml index 190fa4ffc..d09ca4ecd 100644 --- a/.github/workflows/linux_build_node_v8_image.yml +++ b/.github/workflows/linux_build_node_v8_image.yml @@ -22,8 +22,8 @@ env: DOCKERHUB_USERNAME: ${{ secrets.DOCKERHUB_USERNAME }} DOCKERHUB_REPO_JAVET: ${{ secrets.DOCKERHUB_REPO_JAVET }} JAVET_NODE_VERSION: 18.16.0 - JAVET_V8_VERSION: 11.3.244.8 - JAVET_VERSION: 2.1.2 + JAVET_V8_VERSION: 11.4.183.14 + JAVET_VERSION: 2.2.0 # if we skip a job using a job level `if` condition, then any dependent jobs also don't run. # we can skip a step of the job, using a step level `if` condition. diff --git a/README.rst b/README.rst index 2b00af9ea..22edd3bf6 100644 --- a/README.rst +++ b/README.rst @@ -33,7 +33,7 @@ Major Features * Linux (x86_64) + Mac OS (x86_64, arm64) + ️Windows (x86_64) * Android (arm, arm64, x86 and x86_64) -* Node.js ``v18.16.0`` + V8 ``v11.3.244.8`` +* Node.js ``v18.16.0`` + V8 ``v11.4.183.14`` * Dynamic switch between Node.js and V8 mode (`Which mode do you prefer? `_) * Polyfill V8 mode with `Javenode `_ * V8 API exposure in JVM @@ -58,14 +58,14 @@ Maven com.caoccao.javet javet - 2.1.2 + 2.2.0 com.caoccao.javet javet-macos - 2.1.2 + 2.2.0 Gradle Kotlin DSL @@ -73,18 +73,18 @@ Gradle Kotlin DSL .. code-block:: kotlin - implementation("com.caoccao.javet:javet:2.1.2") // Linux and Windows (x86_64) - implementation("com.caoccao.javet:javet-macos:2.1.2") // Mac OS (x86_64 and arm64) - implementation("com.caoccao.javet:javet-android:2.1.2") // Android (arm, arm64, x86 and x86_64) + implementation("com.caoccao.javet:javet:2.2.0") // Linux and Windows (x86_64) + implementation("com.caoccao.javet:javet-macos:2.2.0") // Mac OS (x86_64 and arm64) + implementation("com.caoccao.javet:javet-android:2.2.0") // Android (arm, arm64, x86 and x86_64) Gradle Groovy DSL ^^^^^^^^^^^^^^^^^ .. code-block:: groovy - implementation 'com.caoccao.javet:javet:2.1.2' // Linux and Windows (x86_64) - implementation 'com.caoccao.javet:javet-macos:2.1.2' // Mac OS (x86_64 and arm64) - implementation 'com.caoccao.javet:javet-android:2.1.2' // Android (arm, arm64, x86 and x86_64) + implementation 'com.caoccao.javet:javet:2.2.0' // Linux and Windows (x86_64) + implementation 'com.caoccao.javet:javet-macos:2.2.0' // Mac OS (x86_64 and arm64) + implementation 'com.caoccao.javet:javet-android:2.2.0' // Android (arm, arm64, x86 and x86_64) Hello Javet ----------- diff --git a/android/javet-android/build.gradle.kts b/android/javet-android/build.gradle.kts index da39d89cc..cf8246bd5 100644 --- a/android/javet-android/build.gradle.kts +++ b/android/javet-android/build.gradle.kts @@ -21,7 +21,7 @@ plugins { id("com.android.library") } -version = "2.1.2" +version = "2.2.0" android { compileSdk = 30 diff --git a/android/javet-android/src/main/AndroidManifest.xml b/android/javet-android/src/main/AndroidManifest.xml index eb5797df0..b435c27b2 100644 --- a/android/javet-android/src/main/AndroidManifest.xml +++ b/android/javet-android/src/main/AndroidManifest.xml @@ -2,7 +2,7 @@ \ No newline at end of file diff --git a/android/pom.xml b/android/pom.xml index eefe79b46..d6ef27831 100644 --- a/android/pom.xml +++ b/android/pom.xml @@ -3,7 +3,7 @@ com.caoccao.javet javet-android - 2.1.2 + 2.2.0 javet aar Javet is Java + V8 (JAVa + V + EighT). It is an awesome way of embedding V8 in Java. @@ -29,7 +29,7 @@ scm:git:git://github.com/caoccao/Javet.git scm:git:git@github.com:caoccao/caoccao.git https://github.com/caoccao/Javet - 2.1.2 + 2.2.0 diff --git a/build.gradle.kts b/build.gradle.kts index 78c9bc674..46b3fcdbc 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -25,7 +25,7 @@ repositories { } group = "com.caoccao.javet" -version = "2.1.2" +version = "2.2.0" dependencies { testImplementation("org.eclipse.jetty.websocket:websocket-server:9.4.49.v20220914") diff --git a/cpp/CMakeLists.txt b/cpp/CMakeLists.txt index cf194e529..ccf6c996d 100644 --- a/cpp/CMakeLists.txt +++ b/cpp/CMakeLists.txt @@ -152,7 +152,7 @@ if(CMAKE_SYSTEM_NAME STREQUAL "Windows") set(JAVET_LIB_ARCH x86_64) set(JAVET_LIB_ARCH x86_64) # Generate PDB file - set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} /Zi") + set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} /Zi /MP") set(CMAKE_SHARED_LINKER_FLAGS_RELEASE "${CMAKE_SHARED_LINKER_FLAGS_RELEASE} /DEBUG /OPT:REF /OPT:ICF") add_definitions(-D_ITERATOR_DEBUG_LEVEL=0 -D_WIN32) list(APPEND includeDirs $ENV{JAVA_HOME}/include/win32) @@ -185,6 +185,8 @@ elseif(CMAKE_SYSTEM_NAME STREQUAL "Linux" OR CMAKE_SYSTEM_NAME STREQUAL "Android set(CMAKE_POSITION_INDEPENDENT_CODE ON) add_library(Javet SHARED ${sourceFiles}) add_library(JavetStatic STATIC ${sourceFiles}) + set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wno-invalid-offsetof ") + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wno-invalid-offsetof ") if(CMAKE_SYSTEM_NAME STREQUAL "Linux" AND CMAKE_HOST_SYSTEM_PROCESSOR MATCHES "(arm64|x86_64|aarch64)") set(JAVET_LIB_SYSTEM "linux") if (CMAKE_HOST_SYSTEM_PROCESSOR STREQUAL "x86_64") @@ -240,6 +242,8 @@ elseif(CMAKE_SYSTEM_NAME STREQUAL "Linux" OR CMAKE_SYSTEM_NAME STREQUAL "Android endif() elseif(CMAKE_SYSTEM_NAME STREQUAL "Darwin" AND CMAKE_HOST_SYSTEM_PROCESSOR MATCHES "(arm64|x86_64)") set(JAVET_LIB_SYSTEM "macos") + set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wno-ambiguous-reversed-operator ") + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wno-ambiguous-reversed-operator ") if (CMAKE_HOST_SYSTEM_PROCESSOR STREQUAL "arm64") set(JAVET_LIB_ARCH arm64) add_definitions(-D__arm64__) @@ -275,7 +279,7 @@ elseif(CMAKE_SYSTEM_NAME STREQUAL "Linux" OR CMAKE_SYSTEM_NAME STREQUAL "Android # https://caoccao.blogspot.com/2021/08/jni-symbol-conflicts-in-mac-os.html target_link_libraries(Javet PUBLIC -exported_symbols_list ${CMAKE_SOURCE_DIR}/jni/exported_symbols_list.txt) else() - message(FATAL_ERROR "Linux or Windows (arm64) have not been supported yet.") + message(FATAL_ERROR "Windows (arm64) is not supported.") endif() if(DEFINED JAVET_LIB_ARCH) set_target_properties(JavetStatic PROPERTIES OUTPUT_NAME "${JAVET_LIB_PREFIX}-${JAVET_LIB_TYPE}-${JAVET_LIB_SYSTEM}-${JAVET_LIB_ARCH}.v.${JAVET_VERSION}") @@ -283,7 +287,7 @@ elseif(CMAKE_SYSTEM_NAME STREQUAL "Linux" OR CMAKE_SYSTEM_NAME STREQUAL "Android set_target_properties(JavetStatic PROPERTIES OUTPUT_NAME "${JAVET_LIB_PREFIX}-${JAVET_LIB_TYPE}-${JAVET_LIB_SYSTEM}.v.${JAVET_VERSION}") endif() else() - message(FATAL_ERROR "Linux (x86-64), Mac OS (x86-64, arm64), Windows (x86-64) and Android are the only supported Operating Systems.") + message(FATAL_ERROR "Linux (x86-64, arm64), Mac OS (x86-64, arm64), Windows (x86-64) and Android are the only supported Operating Systems.") endif() if(DEFINED JAVET_LIB_ARCH) diff --git a/cpp/build-android.sh b/cpp/build-android.sh index 889b8e50a..2095f62ee 100755 --- a/cpp/build-android.sh +++ b/cpp/build-android.sh @@ -2,7 +2,7 @@ # Usage for V8: sh build-android.sh -DV8_DIR=${HOME}/v8 -DCMAKE_ANDROID_NDK=${HOME}/android -DCMAKE_ANDROID_ARCH=arm64 # Usage for Node: sh build-android.sh -DNODE_DIR=${HOME}/node -DCMAKE_ANDROID_NDK=${HOME}/android -DCMAKE_ANDROID_ARCH=arm64 -JAVET_VERSION=2.1.2 +JAVET_VERSION=2.2.0 rm -rf build mkdir build cd build diff --git a/cpp/build-linux.sh b/cpp/build-linux.sh index 1308ee9d5..facf26de5 100755 --- a/cpp/build-linux.sh +++ b/cpp/build-linux.sh @@ -2,7 +2,7 @@ # Usage for V8: sh build-linux.sh -DV8_DIR=${HOME}/v8 # Usage for Node: sh build-linux.sh -DNODE_DIR=${HOME}/node -JAVET_VERSION=2.1.2 +JAVET_VERSION=2.2.0 rm -rf build mkdir build cd build diff --git a/cpp/build-macos.sh b/cpp/build-macos.sh index 3502f5913..24e719813 100755 --- a/cpp/build-macos.sh +++ b/cpp/build-macos.sh @@ -2,7 +2,7 @@ # Usage for V8: sh build-macos.sh -DV8_DIR=${HOME}/v8 # Usage for Node: sh build-macos.sh -DNODE_DIR=${HOME}/node -JAVET_VERSION=2.1.2 +JAVET_VERSION=2.2.0 rm -rf build mkdir build cd build diff --git a/cpp/build-windows.cmd b/cpp/build-windows.cmd index f47f08624..4f9299d26 100644 --- a/cpp/build-windows.cmd +++ b/cpp/build-windows.cmd @@ -1,7 +1,7 @@ @echo off REM Usage for V8: build -DV8_DIR=C:\v8 REM Usage for Node: build -DNODE_DIR=C:\node -SET JAVET_VERSION=2.1.2 +SET JAVET_VERSION=2.2.0 rd /s/q build mkdir build cd build diff --git a/cpp/jni/com_caoccao_javet_interop_V8Native.cpp b/cpp/jni/com_caoccao_javet_interop_V8Native.cpp deleted file mode 100644 index f45e325ff..000000000 --- a/cpp/jni/com_caoccao_javet_interop_V8Native.cpp +++ /dev/null @@ -1,2171 +0,0 @@ -/* - * Copyright (c) 2021-2023 caoccao.com Sam Cao - * All rights reserved. - - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - - * http://www.apache.org/licenses/LICENSE-2.0 - - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include "com_caoccao_javet_interop_V8Native.h" -#include "javet_callbacks.h" -#include "javet_converter.h" -#include "javet_enums.h" -#include "javet_exceptions.h" -#include "javet_inspector.h" -#include "javet_monitor.h" -#include "javet_logging.h" -#include "javet_native.h" -#include "javet_node.h" -#include "javet_v8.h" -#include "javet_v8_runtime.h" - - /* - * Development Guide: - * 1. Omitting namespace is not recommended in this project. - * 2. Methods are expected to be sorted alphabatically except JNI_OnLoad. - */ - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_add -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_SET(v8ValueType)) { - auto v8ValueValue = Javet::Converter::ToV8Value(jniEnv, v8Context, value); - auto v8MaybeLocalSet = v8LocalValue.As()->Add(v8Context, v8ValueValue); - if (v8MaybeLocalSet.IsEmpty()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - } -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_allowCodeGenerationFromStrings -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jboolean allow) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - v8Context->AllowCodeGenerationFromStrings(allow); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_await -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jint mAwaitMode) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - auto umAwaitMode = static_cast(mAwaitMode); - return (jboolean)v8Runtime->Await(umAwaitMode); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_call -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject mReceiver, jboolean mResultRequired, jobjectArray mValues) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsFunction()) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - V8MaybeLocalValue v8MaybeLocalValueResult; - auto umReceiver = Javet::Converter::ToV8Value(jniEnv, v8Context, mReceiver); - uint32_t valueCount = mValues == nullptr ? 0 : jniEnv->GetArrayLength(mValues); - if (valueCount > 0) { - auto umValuesPointer = Javet::Converter::ToV8Values(jniEnv, v8Context, mValues); - v8MaybeLocalValueResult = v8LocalValue.As()->Call(v8Context, umReceiver, valueCount, umValuesPointer.get()); - } - else { - v8MaybeLocalValueResult = v8LocalValue.As()->Call(v8Context, umReceiver, 0, nullptr); - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - else if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_callAsConstructor -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobjectArray mValues) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsFunction()) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - V8MaybeLocalValue v8MaybeLocalValueResult; - uint32_t valueCount = mValues == nullptr ? 0 : jniEnv->GetArrayLength(mValues); - if (valueCount > 0) { - auto umValuesPointer = Javet::Converter::ToV8Values(jniEnv, v8Context, mValues); - v8MaybeLocalValueResult = v8LocalValue.As()->CallAsConstructor(v8Context, valueCount, umValuesPointer.get()); - } - else { - v8MaybeLocalValueResult = v8LocalValue.As()->CallAsConstructor(v8Context, 0, nullptr); - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - else if (!v8MaybeLocalValueResult.IsEmpty()) { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_clearInternalStatistic -(JNIEnv* jniEnv, jobject caller) { -#ifdef ENABLE_MONITOR - GlobalJavetNativeMonitor.Clear(); -#endif -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_clearWeak -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_DATA_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (!v8PersistentDataPointer->IsEmpty() && v8PersistentDataPointer->IsWeak()) { - auto v8ValueReference = v8PersistentDataPointer->ClearWeak(); - v8ValueReference->Clear(); - delete v8ValueReference; - INCREASE_COUNTER(Javet::Monitor::CounterType::DeleteWeakCallbackReference); - } -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_cloneV8Value -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jboolean mReferenceCopy) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - V8LocalValue clonedV8LocalValue; - if (!mReferenceCopy - && !v8LocalValue->IsFunction() - && !v8LocalValue->IsMap() - && !v8LocalValue->IsSet() - && !v8LocalValue->IsWeakMap() - && !v8LocalValue->IsWeakSet() - && v8LocalValue->IsObject()) { - /* - * Not all objects can be value copied. - * V8 performs the CHECK(is_clonable_js_type || is_clonable_wasm_type). - * The object actually is shadow copied. - */ - clonedV8LocalValue = v8LocalValue.As()->Clone(); - } - else { - // Reference copy - clonedV8LocalValue = V8LocalValue::New(v8Context->GetIsolate(), v8LocalValue); - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, clonedV8LocalValue); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_closeV8Runtime -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - v8Runtime->ClearExternalException(jniEnv); - v8Runtime->ClearExternalV8Runtime(jniEnv); - delete v8Runtime; - INCREASE_COUNTER(Javet::Monitor::CounterType::DeleteV8Runtime); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_compile -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mScript, jbyteArray mCachedData, jboolean mResultRequired, - jstring mResourceName, jint mResourceLineOffset, jint mResourceColumnOffset, jint mScriptId, jboolean mIsWASM, jboolean mIsModule) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - auto umScript = Javet::Converter::ToV8String(jniEnv, v8Context, mScript); - auto scriptOriginPointer = Javet::Converter::ToV8ScriptOringinPointer( - jniEnv, v8Context, mResourceName, mResourceLineOffset, mResourceColumnOffset, mScriptId, mIsWASM, mIsModule); - if (mIsModule) { - v8::MaybeLocal v8MaybeLocalCompiledModule; - if (mCachedData) { - V8ScriptCompilerSource scriptSource( - umScript, *scriptOriginPointer.get(), Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); - v8MaybeLocalCompiledModule = v8::ScriptCompiler::CompileModule( - v8Context->GetIsolate(), &scriptSource, v8::ScriptCompiler::kConsumeCodeCache); - LOG_DEBUG("Module cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); - } - else { - V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); - v8MaybeLocalCompiledModule = v8::ScriptCompiler::CompileModule(v8Context->GetIsolate(), &scriptSource); - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - else if (mResultRequired && !v8MaybeLocalCompiledModule.IsEmpty()) { - return Javet::Converter::ToExternalV8Module( - jniEnv, v8Runtime, v8Context, v8MaybeLocalCompiledModule.ToLocalChecked()); - } - } - else { - v8::MaybeLocal v8MaybeLocalScript; - if (mCachedData) { - V8ScriptCompilerSource scriptSource( - umScript, *scriptOriginPointer.get(), Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - V8InternalDisallowCompilation v8InternalDisallowCompilation(v8InternalIsolate); - v8MaybeLocalScript = v8::ScriptCompiler::Compile(v8Context, &scriptSource, v8::ScriptCompiler::kConsumeCodeCache); - LOG_DEBUG("Script cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); - } - else { - V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); - v8MaybeLocalScript = v8::ScriptCompiler::Compile(v8Context, &scriptSource); - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - else if (mResultRequired && !v8MaybeLocalScript.IsEmpty()) { - return Javet::Converter::ToExternalV8Script( - jniEnv, v8Runtime, v8Context, v8MaybeLocalScript.ToLocalChecked()); - } - } - return nullptr; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_compileFunction -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mScript, jbyteArray mCachedData, - jstring mResourceName, jint mResourceLineOffset, jint mResourceColumnOffset, jint mScriptId, jboolean mIsWASM, - jobjectArray mArguments, jobjectArray mContextExtensions) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - auto umScript = Javet::Converter::ToV8String(jniEnv, v8Context, mScript); - jboolean isModule = false; - auto scriptOriginPointer = Javet::Converter::ToV8ScriptOringinPointer( - jniEnv, v8Context, mResourceName, mResourceLineOffset, mResourceColumnOffset, mScriptId, mIsWASM, isModule); - size_t argumentCount = 0; - size_t contextExtensionCount = 0; - std::unique_ptr argumentsPointer; - std::unique_ptr contextExtensionsPointer; - if (mArguments != nullptr) { - argumentCount = jniEnv->GetArrayLength(mArguments); - if (argumentCount > 0) { - argumentsPointer = Javet::Converter::ToV8Strings(jniEnv, v8Context, mArguments); - } - } - if (mContextExtensions != nullptr) { - contextExtensionCount = jniEnv->GetArrayLength(mContextExtensions); - if (contextExtensionCount > 0) { - contextExtensionsPointer = Javet::Converter::ToV8Objects(jniEnv, v8Context, mContextExtensions); - } - } - v8::MaybeLocal v8MaybeLocalFunction; - if (mCachedData) { - V8ScriptCompilerSource scriptSource( - umScript, *scriptOriginPointer.get(), Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); - v8MaybeLocalFunction = v8::ScriptCompiler::CompileFunction( - v8Context, &scriptSource, - argumentCount, argumentsPointer.get(), - contextExtensionCount, contextExtensionsPointer.get(), - v8::ScriptCompiler::kConsumeCodeCache); - LOG_DEBUG("Function cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); - } - else { - V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); - v8MaybeLocalFunction = v8::ScriptCompiler::CompileFunction( - v8Context, &scriptSource, - argumentCount, argumentsPointer.get(), - contextExtensionCount, contextExtensionsPointer.get()); - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - else if (!v8MaybeLocalFunction.IsEmpty()) { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalFunction.ToLocalChecked()); - } - return nullptr; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_contextGet -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jint index) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_CONTEXT(v8ValueType)) { - V8LocalContext v8ContextValue = v8LocalValue.As(); - V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); - if (index >= 0 && index < v8InternalContext.length()) { - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - auto v8InternalObject = v8InternalContext.get(index); - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8InternalObject); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_contextGetLength -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_CONTEXT(v8ValueType)) { - V8LocalContext v8ContextValue = v8LocalValue.As(); - V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); - return v8InternalContext.length(); - } - return 0; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_contextIsContextType -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jint contextTypeId) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_CONTEXT(v8ValueType)) { - V8LocalContext v8ContextValue = v8LocalValue.As(); - V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); - using namespace Javet::Enums::V8ContextType; - switch (contextTypeId) { - case Await: return v8InternalContext.IsAwaitContext(); // 0 - case Block: return v8InternalContext.IsBlockContext(); // 1 - case Catch: return v8InternalContext.IsCatchContext(); // 2 - case DebugEvaluate: return v8InternalContext.IsDebugEvaluateContext(); // 3 - case Declaration: return v8InternalContext.is_declaration_context(); // 4 - case Eval: return v8InternalContext.IsEvalContext(); // 5 - case Function: return v8InternalContext.IsFunctionContext(); // 6 - case Module: return v8InternalContext.IsModuleContext(); // 7 - case Script: return v8InternalContext.IsScriptContext(); // 8 - case With: return v8InternalContext.IsWithContext(); // 9 - default:return false; - } - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_contextSetLength -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jint length) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - jboolean success = false; - if (IS_V8_CONTEXT(v8ValueType)) { - V8LocalContext v8ContextValue = v8LocalValue.As(); - V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); - v8InternalContext.set_length(length); - success = true; - } - return success; -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_createV8Inspector -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mV8Inspector) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - v8Runtime->v8Inspector.reset(new Javet::Inspector::JavetInspector(v8Runtime, mV8Inspector)); -} - -/* -Creating multiple isolates allows running JavaScript code in multiple threads, truly parallel. -*/ -JNIEXPORT jlong JNICALL Java_com_caoccao_javet_interop_V8Native_createV8Runtime -(JNIEnv* jniEnv, jobject caller, jobject mRuntimeOptions) { -#ifdef ENABLE_NODE - auto v8Runtime = new Javet::V8Runtime(Javet::V8Native::GlobalV8Platform.get(), Javet::NodeNative::GlobalNodeArrayBufferAllocator); -#else - auto v8Runtime = new Javet::V8Runtime(Javet::V8Native::GlobalV8Platform.get()); -#endif - INCREASE_COUNTER(Javet::Monitor::CounterType::NewV8Runtime); - v8Runtime->CreateV8Isolate(); - v8Runtime->CreateV8Context(jniEnv, mRuntimeOptions); - return TO_JAVA_LONG(v8Runtime); -} - -/* -It only supports Object, Array, Function, Map, Set for now. -Error, Promise, RegExp, Proxy, Symbol, etc. are not supported. -*/ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_createV8Value -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jint v8ValueType, jobject mContext) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - V8LocalValue v8LocalValueResult; - if (IS_V8_OBJECT(v8ValueType)) { - v8LocalValueResult = v8::Object::New(v8Context->GetIsolate()); - } - else if (IS_V8_ARRAY(v8ValueType)) { - v8LocalValueResult = v8::Array::New(v8Context->GetIsolate()); - } - else if (IS_V8_ARRAY_BUFFER(v8ValueType)) { - if (Javet::Converter::IsV8ValueInteger(jniEnv, mContext)) { - v8LocalValueResult = v8::ArrayBuffer::New(v8Context->GetIsolate(), Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, mContext)); - } - else if (Javet::Converter::IsJavaByteBuffer(jniEnv, mContext)) { - std::unique_ptr v8BackingStorePointer = v8::ArrayBuffer::NewBackingStore( - jniEnv->GetDirectBufferAddress(mContext), - static_cast(jniEnv->GetDirectBufferCapacity(mContext)), - [](void*, size_t, void*) {}, - nullptr); - v8LocalValueResult = v8::ArrayBuffer::New(v8Context->GetIsolate(), std::move(v8BackingStorePointer)); - } - } - else if (IS_V8_FUNCTION(v8ValueType)) { - auto javetCallbackContextReferencePointer = new Javet::Callback::JavetCallbackContextReference(jniEnv, mContext); - INCREASE_COUNTER(Javet::Monitor::CounterType::NewJavetCallbackContextReference); - auto v8LocalContextHandle = v8::BigInt::New(v8Context->GetIsolate(), TO_NATIVE_INT_64(javetCallbackContextReferencePointer)); - javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer = new V8PersistentBigInt(v8Context->GetIsolate(), v8LocalContextHandle); - INCREASE_COUNTER(Javet::Monitor::CounterType::NewPersistentCallbackContextReference); - auto v8MaybeLocalFunction = v8::Function::New(v8Context, Javet::Callback::JavetFunctionCallback, v8LocalContextHandle); - if (v8MaybeLocalFunction.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context, "function allocation failed")) { - return nullptr; - } - } - else { - v8LocalValueResult = v8MaybeLocalFunction.ToLocalChecked(); - } - javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer->SetWeak( - javetCallbackContextReferencePointer, Javet::Callback::JavetCloseWeakCallbackContextHandle, v8::WeakCallbackType::kParameter); - } - else if (IS_V8_MAP(v8ValueType)) { - v8LocalValueResult = v8::Map::New(v8Context->GetIsolate()); - } - else if (IS_V8_PROMISE(v8ValueType)) { - auto v8MaybeLocalPromiseResolver = v8::Promise::Resolver::New(v8Context); - if (v8MaybeLocalPromiseResolver.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context, "promise resolver allocation failed")) { - return nullptr; - } - } - else { - v8LocalValueResult = v8MaybeLocalPromiseResolver.ToLocalChecked(); - } - } - else if (IS_V8_PROXY(v8ValueType)) { - V8LocalObject v8LocalObjectObject = mContext == nullptr - ? v8::Object::New(v8Context->GetIsolate()) - : Javet::Converter::ToV8Value(jniEnv, v8Context, mContext).As(); - auto v8LocalObjectHandler = v8::Object::New(v8Context->GetIsolate()); - auto v8MaybeLocalProxy = v8::Proxy::New(v8Context, v8LocalObjectObject, v8LocalObjectHandler); - if (v8MaybeLocalProxy.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context, "proxy allocation failed")) { - return nullptr; - } - } - else { - v8LocalValueResult = v8MaybeLocalProxy.ToLocalChecked(); - } - } - else if (IS_V8_SET(v8ValueType)) { - v8LocalValueResult = v8::Set::New(v8Context->GetIsolate()); - } - else if (IS_V8_SYMBOL(v8ValueType)) { - auto mDescription = (jstring)mContext; - auto v8LocalValueDescription = Javet::Converter::ToV8String(jniEnv, v8Context, mDescription); - v8LocalValueResult = v8::Symbol::New(v8Context->GetIsolate(), v8LocalValueDescription); - } - if (!v8LocalValueResult.IsEmpty()) { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalValueResult); - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_delete -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - V8MaybeBool v8MaybeBool = v8::Just(false); - auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); - if (IS_V8_ARRAY(v8ValueType)) { - if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); - v8MaybeBool = v8LocalValue.As()->Delete(v8Context, integerKey); - } - else { - v8MaybeBool = v8LocalValue.As()->Delete(v8Context, v8ValueKey); - } - } - else if (IS_V8_MAP(v8ValueType)) { - v8MaybeBool = v8LocalValue.As()->Delete(v8Context, v8ValueKey); - } - else if (IS_V8_SET(v8ValueType)) { - v8MaybeBool = v8LocalValue.As()->Delete(v8Context, v8ValueKey); - } - else if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); - v8MaybeBool = v8LocalObject->Delete(v8Context, integerKey); - } - else { - v8MaybeBool = v8LocalObject->Delete(v8Context, v8ValueKey); - } - } - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_deletePrivateProperty -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mKey) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsObject()) { - auto v8LocalStringKey = Javet::Converter::ToV8String(jniEnv, v8Context, mKey); - auto v8LocalPrivateKey = v8::Private::ForApi(v8Context->GetIsolate(), v8LocalStringKey); - auto v8MaybeBool = v8LocalValue.As()->DeletePrivate(v8Context, v8LocalPrivateKey); - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_equals -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle1, jlong v8ValueHandle2) { - RUNTIME_AND_2_VALUES_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle1, v8ValueHandle2); - V8MaybeBool v8MaybeBool = v8LocalValue1->Equals(v8Context, v8LocalValue2); - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_execute -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mScript, jbyteArray mCachedData, jboolean mResultRequired, - jstring mResourceName, jint mResourceLineOffset, jint mResourceColumnOffset, jint mScriptId, jboolean mIsWASM, jboolean mIsModule) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - auto umScript = Javet::Converter::ToV8String(jniEnv, v8Context, mScript); - auto scriptOriginPointer = Javet::Converter::ToV8ScriptOringinPointer( - jniEnv, v8Context, mResourceName, mResourceLineOffset, mResourceColumnOffset, mScriptId, mIsWASM, mIsModule); - if (mIsModule) { - v8::MaybeLocal v8MaybeLocalCompiledModule; - if (mCachedData) { - V8ScriptCompilerSource scriptSource( - umScript, *scriptOriginPointer.get(), Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); - v8MaybeLocalCompiledModule = v8::ScriptCompiler::CompileModule( - v8Context->GetIsolate(), &scriptSource, v8::ScriptCompiler::kConsumeCodeCache); - LOG_DEBUG("Module cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); - } - else { - V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); - v8MaybeLocalCompiledModule = v8::ScriptCompiler::CompileModule(v8Context->GetIsolate(), &scriptSource); - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - else if (!v8MaybeLocalCompiledModule.IsEmpty()) { - auto compliedModule = v8MaybeLocalCompiledModule.ToLocalChecked(); - auto v8MaybeBool = compliedModule->InstantiateModule(v8Context, Javet::Callback::JavetModuleResolveCallback); - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - else if (v8MaybeBool.FromMaybe(false)) { - auto v8MaybeLocalValueResult = compliedModule->Evaluate(v8Context); - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { - Javet::Exceptions::ClearJNIException(jniEnv); - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - } - } - } - else { - v8::MaybeLocal v8MaybeLocalScript; - if (mCachedData) { - V8ScriptCompilerSource scriptSource( - umScript, *scriptOriginPointer.get(), Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - V8InternalDisallowCompilation v8InternalDisallowCompilation(v8InternalIsolate); - v8MaybeLocalScript = v8::ScriptCompiler::Compile(v8Context, &scriptSource, v8::ScriptCompiler::kConsumeCodeCache); - LOG_DEBUG("Script cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); - } - else { - V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); - v8MaybeLocalScript = v8::ScriptCompiler::Compile(v8Context, &scriptSource); - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - else if (!v8MaybeLocalScript.IsEmpty()) { - auto compliedScript = v8MaybeLocalScript.ToLocalChecked(); - auto v8MaybeLocalValueResult = compliedScript->Run(v8Context); - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { - Javet::Exceptions::ClearJNIException(jniEnv); - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - } - } - Javet::Exceptions::ClearJNIException(jniEnv); - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionCanDiscardCompiled -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { - return v8InternalShared.CanDiscardCompiled(); - } - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionCopyScopeInfoFrom -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, - jlong targetV8ValueHandle, jint targetV8ValueType, - jlong sourceV8ValueHandle, jint sourceV8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, targetV8ValueHandle); - jboolean success = false; - if (IS_V8_FUNCTION(targetV8ValueType) && IS_V8_FUNCTION(sourceV8ValueType)) { - auto sourceV8PersistentValuePointer = TO_V8_PERSISTENT_VALUE_POINTER(sourceV8ValueHandle); - auto sourceV8LocalValue = sourceV8PersistentValuePointer->Get(v8Context->GetIsolate()); - auto targetV8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto sourceV8InternalFunction = Javet::Converter::ToV8InternalJSFunction(sourceV8LocalValue); - auto targetV8InternalShared = targetV8InternalFunction.shared(); - auto sourceV8InternalShared = sourceV8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(sourceV8InternalShared) && IS_USER_DEFINED_FUNCTION(targetV8InternalShared)) { - V8InternalDisallowGarbageCollection disallowGarbageCollection; - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - // Clone the shared function info - targetV8InternalShared = *v8InternalIsolate->factory()->CloneSharedFunctionInfo( - v8::internal::Handle(sourceV8InternalShared, v8InternalIsolate)); - // Clone the scope info - auto sourceScopeInfo = sourceV8InternalShared.scope_info(); - auto emptyBlocklistHandle = V8InternalStringSet::New(v8InternalIsolate); - auto targetScopeInfo = *V8InternalScopeInfo::RecreateWithBlockList( - v8InternalIsolate, v8::internal::Handle(sourceScopeInfo, v8InternalIsolate), emptyBlocklistHandle); - targetV8InternalShared.set_raw_scope_info(targetScopeInfo); - targetV8InternalFunction.set_shared(targetV8InternalShared, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); - success = true; - } - } - return success; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionDiscardCompiled -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { - if (v8InternalShared.CanDiscardCompiled()) { - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - V8InternalSharedFunctionInfo::DiscardCompiled(v8InternalIsolate, v8::internal::Handle(v8InternalShared, v8InternalIsolate)); - return true; - } - } - } - return false; -} - -JNIEXPORT jobjectArray JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetArguments -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared) && v8InternalShared.is_wrapped()) { - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); - auto wrappedArguments = v8InternalScript.wrapped_arguments(); - auto length = wrappedArguments.length(); - if (length > 0) { - jobjectArray arguments = jniEnv->NewObjectArray(length, Javet::Converter::jclassString, nullptr); - for (int i = 0; i < length; ++i) { - auto v8InternalObjectHandle = v8::internal::Handle(wrappedArguments.get(i), v8InternalIsolate); - auto v8LocalString = v8::Utils::ToLocal(v8InternalObjectHandle).As(); - jstring argument = Javet::Converter::ToJavaString(jniEnv, v8Context, v8LocalString); - jniEnv->SetObjectArrayElement(arguments, i, argument); - } - return arguments; - } - } - } - return nullptr; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetContext -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - if (v8InternalFunction.has_context()) { - auto v8InternalContextHandle = v8::internal::Handle(v8InternalFunction.context(), v8InternalIsolate); - auto v8LocalContext = v8::Utils::ToLocal(v8InternalContextHandle); - return Javet::Converter::ToExternalV8Context(jniEnv, v8Runtime, v8Context, v8LocalContext); - } - } - return nullptr; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetScopeInfos -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, - jboolean includeGlobalVariables, jboolean includeScopeTypeGlobal) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - V8LocalArray v8LocalArray = v8::Array::New(v8Context->GetIsolate()); - if (IS_V8_FUNCTION(v8ValueType)) { - V8InternalDisallowGarbageCollection disallowGarbageCollection; - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - auto v8InternalScopeInfo = v8InternalShared.scope_info(); - V8InternalScopeIterator scopeIterator(v8InternalIsolate, v8::internal::Handle(v8InternalFunction, v8InternalIsolate)); - uint32_t index = 0; - for (; !scopeIterator.Done(); scopeIterator.Next()) { - auto type = scopeIterator.Type(); - if (!includeScopeTypeGlobal && type == V8InternalScopeIterator::ScopeTypeGlobal) { - continue; - } - V8LocalArray innerV8LocalArray = v8::Array::New(v8Context->GetIsolate(), INDEX_SCOPE_SIZE); - auto mode = includeGlobalVariables ? V8InternalScopeIterator::Mode::ALL : V8InternalScopeIterator::Mode::STACK; - auto scopeObject = scopeIterator.ScopeObject(mode); - auto v8LocalScopeObject = v8::Utils::ToLocal(scopeObject); - innerV8LocalArray->Set(v8Context, INDEX_SCOPE_TYPE, Javet::Converter::ToV8Integer(v8Context, (int)type)).ToChecked(); - innerV8LocalArray->Set(v8Context, INDEX_SCOPE_OBJECT, v8LocalScopeObject).ToChecked(); - innerV8LocalArray->Set(v8Context, INDEX_SCOPE_HAS_CONTEXT, Javet::Converter::ToV8Boolean(v8Context, scopeIterator.HasContext())).ToChecked(); - innerV8LocalArray->Set(v8Context, INDEX_SCOPE_START_POSITION, Javet::Converter::ToV8Integer(v8Context, scopeIterator.start_position())).ToChecked(); - innerV8LocalArray->Set(v8Context, INDEX_SCOPE_END_POSITION, Javet::Converter::ToV8Integer(v8Context, scopeIterator.end_position())).ToChecked(); - v8LocalArray->Set(v8Context, index, innerV8LocalArray).ToChecked(); - ++index; - } - } - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalArray); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetScriptSource -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - V8InternalDisallowGarbageCollection disallowGarbageCollection; - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { - auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); - auto v8InternalSource = V8InternalString::cast(v8InternalScript.source()); - const int startPosition = v8InternalShared.StartPosition(); - const int endPosition = v8InternalShared.EndPosition(); - const int sourceLength = v8InternalSource.length(); - auto sourceCode = v8InternalSource.ToCString( - V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL, - 0, sourceLength); - return jniEnv->NewObject( - Javet::Converter::jclassIV8ValueFunctionScriptSource, - Javet::Converter::jmethodIDIV8ValueFunctionScriptSourceConstructor, - Javet::Converter::ToJavaString(jniEnv, sourceCode.get()), - startPosition, - endPosition); - } - } - return nullptr; -} - -JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetSourceCode -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { - auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); - auto v8InternalSource = V8InternalString::cast(v8InternalScript.source()); - const int startPosition = v8InternalShared.StartPosition(); - const int endPosition = v8InternalShared.EndPosition(); - auto sourceCode = v8InternalSource.ToCString( - V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL, - startPosition, endPosition - startPosition); - return Javet::Converter::ToJavaString(jniEnv, sourceCode.get()); - } - } - return nullptr; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionIsCompiled -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { - return v8InternalShared.is_compiled(); - } - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionIsWrapped -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { - return v8InternalShared.is_wrapped(); - } - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetContext -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject mV8ContextValue) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - jboolean success = false; - if (IS_V8_FUNCTION(v8ValueType)) { - V8InternalDisallowGarbageCollection disallowGarbageCollection; - V8LocalContext v8ContextValue = Javet::Converter::ToV8Context(jniEnv, v8Context, mV8ContextValue); - V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - v8InternalFunction.set_context(v8InternalContext); - success = true; - } - return success; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetScriptSource -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject mScriptSource, jboolean mCloneScript) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - jboolean success = false; - if (IS_V8_FUNCTION(v8ValueType)) { - V8InternalDisallowGarbageCollection disallowGarbageCollection; - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { - auto v8InternalScopeInfo = v8InternalShared.scope_info(); - if (v8InternalScopeInfo.scope_type() == V8InternalScopeType::FUNCTION_SCOPE) { - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - auto mSourceCode = (jstring)jniEnv->CallObjectMethod(mScriptSource, Javet::Converter::jmethodIDIV8ValueFunctionScriptGetCode); - auto umSourceCode = Javet::Converter::ToV8String(jniEnv, v8Context, mSourceCode); - const int startPosition = jniEnv->CallIntMethod(mScriptSource, Javet::Converter::jmethodIDIV8ValueFunctionScriptGetStartPosition); - const int endPosition = jniEnv->CallIntMethod(mScriptSource, Javet::Converter::jmethodIDIV8ValueFunctionScriptGetEndPosition); - auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); - auto v8InternalSource = v8::Utils::OpenHandle(*umSourceCode); - bool sourceCodeEquals = v8InternalScript.source().StrictEquals(*v8InternalSource); - bool positionEquals = startPosition == v8InternalShared.StartPosition() && endPosition == v8InternalShared.EndPosition(); - if (!sourceCodeEquals || !positionEquals) { - if (v8InternalShared.CanDiscardCompiled()) { - V8InternalSharedFunctionInfo::DiscardCompiled(v8InternalIsolate, v8::internal::Handle(v8InternalShared, v8InternalIsolate)); - v8InternalShared.set_allows_lazy_compilation(true); - } - if (!sourceCodeEquals) { - if (mCloneScript) { - auto clonedV8InternalScript = v8InternalIsolate->factory()->CloneScript(v8::internal::Handle(v8InternalScript, v8InternalIsolate)); - clonedV8InternalScript->set_source(*v8InternalSource, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); - v8InternalShared.set_script(*clonedV8InternalScript); - } - else { - v8InternalScript.set_source(*v8InternalSource, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); - } - } - if (!positionEquals) { - v8InternalScopeInfo.SetPositionInfo(startPosition, endPosition); - } - success = true; - } - DELETE_LOCAL_REF(jniEnv, mSourceCode); - } - } - } - return success; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetSourceCode -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mSourceCode, jboolean mCloneScript) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - jboolean success = false; - if (IS_V8_FUNCTION(v8ValueType)) { - V8InternalDisallowGarbageCollection disallowGarbageCollection; - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { - auto v8InternalScopeInfo = v8InternalShared.scope_info(); - while (v8InternalScopeInfo.scope_type() == V8InternalScopeType::FUNCTION_SCOPE) { - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); - auto v8InternalSource = V8InternalString::cast(v8InternalScript.source()); - const int startPosition = v8InternalShared.StartPosition(); - const int endPosition = v8InternalShared.EndPosition(); - const int sourceLength = v8InternalSource.length(); - - // Build the new source code. - auto umSourceCode = Javet::Converter::ToV8String(jniEnv, v8Context, mSourceCode); - - V8LocalString newSourceCode; - if (startPosition > 0) { - int utf8Length = 0; - auto stdStringHeader(v8InternalSource.ToCString( - V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL, - 0, startPosition, &utf8Length)); - auto v8MaybeLocalStringHeader = v8::String::NewFromUtf8( - v8Context->GetIsolate(), stdStringHeader.get(), v8::NewStringType::kNormal, utf8Length); - if (v8MaybeLocalStringHeader.IsEmpty()) { - Javet::Exceptions::HandlePendingException( - jniEnv, v8Runtime, v8Context, "header could not be extracted from the source code"); - break; - } - newSourceCode = v8MaybeLocalStringHeader.ToLocalChecked(); - } - if (newSourceCode.IsEmpty()) { - newSourceCode = umSourceCode; - } - else { - newSourceCode = v8::String::Concat(v8Context->GetIsolate(), newSourceCode, umSourceCode); - } - if (endPosition < sourceLength) { - int utf8Length = 0; - auto stdStringFooter(v8InternalSource.ToCString( - V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL, - endPosition, sourceLength - endPosition, &utf8Length)); - auto v8MaybeLocalStringFooter = v8::String::NewFromUtf8( - v8Context->GetIsolate(), stdStringFooter.get(), v8::NewStringType::kNormal, utf8Length); - if (v8MaybeLocalStringFooter.IsEmpty()) { - Javet::Exceptions::HandlePendingException( - jniEnv, v8Runtime, v8Context, "footer could not be extracted from the source code"); - break; - } - auto v8LocalStringFooter = v8MaybeLocalStringFooter.ToLocalChecked(); - if (newSourceCode.IsEmpty()) { - newSourceCode = v8LocalStringFooter; - } - else { - newSourceCode = v8::String::Concat(v8Context->GetIsolate(), newSourceCode, v8LocalStringFooter); - } - } - - /* - * Set the source and update the start and end position. - * Note: The source code is shared among all script objects, but position info is not. - * So the caller is responsible for restoring the original source code, - * otherwise the next script execution will likely fail because the position info - * of the next script is incorrect. - */ - const int newSourceLength = umSourceCode->Length(); - const int newEndPosition = startPosition + newSourceLength; - - auto newV8InternalSource = v8::Utils::OpenHandle(*newSourceCode); - bool sourceCodeEquals = v8InternalSource.StrictEquals(*newV8InternalSource); - bool positionEquals = newEndPosition == v8InternalShared.EndPosition(); - - if (!sourceCodeEquals || !positionEquals) { - // Discard compiled data and set lazy compile. - if (v8InternalShared.CanDiscardCompiled()) { - V8InternalSharedFunctionInfo::DiscardCompiled(v8InternalIsolate, v8::internal::Handle(v8InternalShared, v8InternalIsolate)); - v8InternalShared.set_allows_lazy_compilation(true); - } - if (!sourceCodeEquals) { - if (mCloneScript) { - auto clonedV8InternalScript = v8InternalIsolate->factory()->CloneScript(v8::internal::Handle(v8InternalScript, v8InternalIsolate)); - clonedV8InternalScript->set_source(*newV8InternalSource, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); - v8InternalShared.set_script(*clonedV8InternalScript); - } - else { - v8InternalScript.set_source(*newV8InternalSource, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); - } - } - if (!positionEquals) { - v8InternalScopeInfo.SetPositionInfo(startPosition, newEndPosition); - } - success = true; - } - break; - } - } - } - return success; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_get -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - auto v8LocalValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); - V8MaybeLocalValue v8MaybeLocalValueResult; - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - if (IS_V8_ARGUMENTS(v8ValueType) || IS_V8_ARRAY(v8ValueType) || v8LocalValue->IsTypedArray()) { - if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); - if (integerKey >= 0) { - v8MaybeLocalValueResult = v8LocalValue.As()->Get(v8Context, integerKey); - } - } - else if (v8LocalValueKey.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - v8MaybeLocalValueResult = v8LocalValue.As()->Get(v8Context, v8LocalValueKey); - } - } - else if (v8LocalValueKey.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - if (IS_V8_SYMBOL(v8ValueType)) { - auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); - if (v8MaybeLocalValue.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); - } - } - if (IS_V8_MAP(v8ValueType)) { - v8MaybeLocalValueResult = v8LocalValue.As()->Get(v8Context, v8LocalValueKey); - } - else if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); - v8MaybeLocalValueResult = v8LocalObject->Get(v8Context, integerKey); - } - else { - v8MaybeLocalValueResult = v8LocalObject->Get(v8Context, v8LocalValueKey); - } - } - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - if (v8MaybeLocalValueResult.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jbyteArray JNICALL Java_com_caoccao_javet_interop_V8Native_getCachedData -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - std::unique_ptr cachedDataPointer; - if (IS_V8_SCRIPT(v8ValueType)) { - RUNTIME_AND_SCRIPT_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (!v8LocalScript.IsEmpty()) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - cachedDataPointer.reset(v8::ScriptCompiler::CreateCodeCache(v8LocalScript->GetUnboundScript())); - if (v8TryCatch.HasCaught()) { - Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - return nullptr; - } - } - } - else if (IS_V8_FUNCTION(v8ValueType)) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { - auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); - if (v8InternalScript.is_wrapped()) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - cachedDataPointer.reset(v8::ScriptCompiler::CreateCodeCacheForFunction(v8LocalValue.As())); - if (v8TryCatch.HasCaught()) { - Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - return nullptr; - } - } - } - } - else if (IS_V8_MODULE(v8ValueType)) { - RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - cachedDataPointer.reset(v8::ScriptCompiler::CreateCodeCache(v8LocalModule->GetUnboundModuleScript())); - if (v8TryCatch.HasCaught()) { - Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - return nullptr; - } - } - if (cachedDataPointer) { - return Javet::Converter::ToJavaByteArray(jniEnv, cachedDataPointer.get()); - } - return nullptr; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getGlobalObject -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - return Javet::Converter::ToExternalV8ValueGlobalObject(jniEnv, v8Runtime); -} - -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getIdentityHash -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsObject()) { - return v8LocalValue.As()->GetIdentityHash(); - } - return 0; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getInternalProperties -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - // This feature is not enabled yet. - v8_inspector::V8InspectorClient v8InspectorClient; - v8_inspector::V8InspectorImpl v8InspectorImpl(v8Context->GetIsolate(), &v8InspectorClient); - v8_inspector::V8Debugger v8Debugger(v8Context->GetIsolate(), &v8InspectorImpl); - auto v8MaybeLocalArray = v8Debugger.internalProperties(v8Context, v8LocalValue.As()); - if (v8MaybeLocalArray.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalArray.ToLocalChecked()); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jlongArray JNICALL Java_com_caoccao_javet_interop_V8Native_getInternalStatistic -(JNIEnv* jniEnv, jobject caller) { -#ifdef ENABLE_MONITOR - return GlobalJavetNativeMonitor.GetCounters(jniEnv); -#else - return nullptr; -#endif -} - -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getJSFunctionType -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - using namespace Javet::Enums::JSFunctionType; - if (IS_V8_FUNCTION(v8ValueType)) { - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - if (v8InternalShared.native()) { - return JSFunctionType::Native; - } - else if (v8InternalShared.IsApiFunction()) { - return JSFunctionType::API; - } - else if (v8InternalShared.IsUserJavaScript()) { - return JSFunctionType::UserDefined; - } - } - return JSFunctionType::Unknown; -} - -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getJSScopeType -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_FUNCTION(v8ValueType)) { - auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); - auto v8InternalShared = v8InternalFunction.shared(); - auto v8InternalScopeInfo = v8InternalShared.scope_info(); - return v8InternalScopeInfo.scope_type(); - } - return Javet::Enums::JSScopeType::Unknown; -} - -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getLength -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_ARRAY(v8ValueType)) { - return (jint)v8LocalValue.As()->Length(); - } - if (v8LocalValue->IsTypedArray()) { - return (jint)v8LocalValue.As()->Length(); - } - return 0; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getOwnPropertyNames -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_SYMBOL(v8ValueType)) { - auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); - if (v8MaybeLocalValue.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); - } - } - if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - auto v8MaybeLocalArray = v8LocalObject->GetOwnPropertyNames(v8Context); - if (v8MaybeLocalArray.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalArray.ToLocalChecked()); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getPrivateProperty -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mKey) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsObject()) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - auto v8LocalStringKey = Javet::Converter::ToV8String(jniEnv, v8Context, mKey); - auto v8LocalPrivateKey = v8::Private::ForApi(v8Context->GetIsolate(), v8LocalStringKey); - auto v8MaybeLocalValue = v8LocalValue.As()->GetPrivate(v8Context, v8LocalPrivateKey); - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - if (v8MaybeLocalValue.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValue.ToLocalChecked()); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getPropertyNames -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_SYMBOL(v8ValueType)) { - auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); - if (v8MaybeLocalValue.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); - } - } - if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - auto v8MaybeLocalArray = v8LocalObject->GetPropertyNames(v8Context); - if (v8MaybeLocalArray.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalArray.ToLocalChecked()); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getProperty -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_SYMBOL(v8ValueType)) { - auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); - if (v8MaybeLocalValue.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); - } - } - if (v8LocalValue->IsObject()) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - auto v8LocalObject = v8LocalValue.As(); - V8MaybeLocalValue v8MaybeLocalValueValue; - if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); - v8MaybeLocalValueValue = v8LocalObject->Get(v8Context, integerKey); - } - else { - auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); - if (v8ValueKey.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - v8MaybeLocalValueValue = v8LocalObject->Get(v8Context, v8ValueKey); - } - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - if (v8MaybeLocalValueValue.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueValue.ToLocalChecked()); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getPrototype -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - V8LocalValue v8LocalValueResult = v8LocalObject->GetPrototype(); - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalValueResult); - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getSize -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_MAP(v8ValueType)) { - return (jint)v8LocalValue.As()->Size(); - } - if (IS_V8_SET(v8ValueType)) { - return (jint)v8LocalValue.As()->Size(); - } - return 0; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8HeapSpaceStatistics -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jint allocationSpace) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - return Javet::Monitor::GetHeapSpaceStatistics(jniEnv, v8Runtime->v8Isolate, allocationSpace); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8HeapStatistics -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - return Javet::Monitor::GetHeapStatistics(jniEnv, v8Runtime->v8Isolate); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8SharedMemoryStatistics -(JNIEnv* jniEnv, jobject caller) { - return Javet::Monitor::GetV8SharedMemoryStatistics(jniEnv); -} - -JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_getVersion -(JNIEnv* jniEnv, jobject caller) { - return Javet::Converter::ToJavaString(jniEnv, v8::V8::GetVersion()); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_has -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - auto v8LocalValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, value); - if (!v8LocalValueKey.IsEmpty()) { - V8MaybeBool v8MaybeBool = v8::Just(false); - if (IS_V8_MAP(v8ValueType)) { - v8MaybeBool = v8LocalValue.As()->Has(v8Context, v8LocalValueKey); - } - else if (IS_V8_SET(v8ValueType)) { - v8MaybeBool = v8LocalValue.As()->Has(v8Context, v8LocalValueKey); - } - else if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - if (Javet::Converter::IsV8ValueInteger(jniEnv, value)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, value); - v8MaybeBool = v8LocalObject->Has(v8Context, integerKey); - } - else { - v8MaybeBool = v8LocalObject->Has(v8Context, v8LocalValueKey); - } - } - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasInternalType -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueInternalType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - using namespace Javet::Enums::V8ValueInternalType; - switch (v8ValueInternalType) - { - case V8ValueInternalType::Undefined: return v8LocalValue->IsUndefined(); // 0 - case V8ValueInternalType::Null: return v8LocalValue->IsNull(); // 1 - case V8ValueInternalType::NullOrUndefined: return v8LocalValue->IsNullOrUndefined(); // 2 - case V8ValueInternalType::True: return v8LocalValue->IsTrue(); // 3 - case V8ValueInternalType::False: return v8LocalValue->IsFalse(); // 4 - case V8ValueInternalType::Name: return v8LocalValue->IsName(); // 5 - case V8ValueInternalType::String: return v8LocalValue->IsString(); // 6 - case V8ValueInternalType::Symbol: return v8LocalValue->IsSymbol(); // 7 - case V8ValueInternalType::Function: return v8LocalValue->IsFunction(); // 8 - case V8ValueInternalType::Array: return v8LocalValue->IsArray(); // 9 - case V8ValueInternalType::Object: return v8LocalValue->IsObject(); // 10 - case V8ValueInternalType::BigInt: return v8LocalValue->IsBigInt(); // 11 - case V8ValueInternalType::Boolean: return v8LocalValue->IsBoolean(); // 12 - case V8ValueInternalType::Number: return v8LocalValue->IsNumber(); // 13 - case V8ValueInternalType::External: return v8LocalValue->IsExternal(); // 14 - case V8ValueInternalType::Int32: return v8LocalValue->IsInt32(); // 15 - case V8ValueInternalType::Date: return v8LocalValue->IsDate(); // 16 - case V8ValueInternalType::ArgumentsObject: return v8LocalValue->IsArgumentsObject(); // 17 - case V8ValueInternalType::BigIntObject: return v8LocalValue->IsBigIntObject(); // 18 - case V8ValueInternalType::BooleanObject: return v8LocalValue->IsBooleanObject(); // 19 - case V8ValueInternalType::NumberObject: return v8LocalValue->IsNumberObject(); // 20 - case V8ValueInternalType::StringObject: return v8LocalValue->IsStringObject(); // 21 - case V8ValueInternalType::SymbolObject: return v8LocalValue->IsSymbolObject(); // 22 - case V8ValueInternalType::NativeError: return v8LocalValue->IsNativeError(); // 23 - case V8ValueInternalType::RegExp: return v8LocalValue->IsRegExp(); // 24 - case V8ValueInternalType::AsyncFunction: return v8LocalValue->IsAsyncFunction(); // 25 - case V8ValueInternalType::GeneratorFunction: return v8LocalValue->IsGeneratorFunction(); // 26 - case V8ValueInternalType::GeneratorObject: return v8LocalValue->IsGeneratorObject(); // 27 - case V8ValueInternalType::Promise: return v8LocalValue->IsPromise(); // 28 - case V8ValueInternalType::Map: return v8LocalValue->IsMap(); // 29 - case V8ValueInternalType::Set: return v8LocalValue->IsSet(); // 30 - case V8ValueInternalType::MapIterator: return v8LocalValue->IsMapIterator(); // 31 - case V8ValueInternalType::SetIterator: return v8LocalValue->IsSetIterator(); // 32 - case V8ValueInternalType::WeakMap: return v8LocalValue->IsWeakMap(); // 33 - case V8ValueInternalType::WeakSet: return v8LocalValue->IsWeakSet(); // 34 - case V8ValueInternalType::ArrayBuffer: return v8LocalValue->IsArrayBuffer(); // 35 - case V8ValueInternalType::ArrayBufferView: return v8LocalValue->IsArrayBufferView(); // 36 - case V8ValueInternalType::TypedArray: return v8LocalValue->IsTypedArray(); // 37 - case V8ValueInternalType::Uint8Array: return v8LocalValue->IsUint8Array(); // 38 - case V8ValueInternalType::Uint8ClampedArray: return v8LocalValue->IsUint8ClampedArray(); // 39 - case V8ValueInternalType::Int8Array: return v8LocalValue->IsInt8Array(); // 40 - case V8ValueInternalType::Uint16Array: return v8LocalValue->IsUint16Array(); // 41 - case V8ValueInternalType::Int16Array: return v8LocalValue->IsInt16Array(); // 42 - case V8ValueInternalType::Uint32Array: return v8LocalValue->IsUint32Array(); // 43 - case V8ValueInternalType::Int32Array: return v8LocalValue->IsInt32Array(); // 44 - case V8ValueInternalType::Float32Array: return v8LocalValue->IsFloat32Array(); // 45 - case V8ValueInternalType::Float64Array: return v8LocalValue->IsFloat64Array(); // 46 - case V8ValueInternalType::BigInt64Array: return v8LocalValue->IsBigInt64Array(); // 47 - case V8ValueInternalType::BigUint64Array: return v8LocalValue->IsBigUint64Array(); // 48 - case V8ValueInternalType::DataView: return v8LocalValue->IsDataView(); // 49 - case V8ValueInternalType::SharedArrayBuffer: return v8LocalValue->IsSharedArrayBuffer(); // 50 - case V8ValueInternalType::Proxy: return v8LocalValue->IsProxy(); // 51 - case V8ValueInternalType::WasmModuleObject: return v8LocalValue->IsWasmModuleObject(); // 52 - case V8ValueInternalType::ModuleNamespaceObject: return v8LocalValue->IsModuleNamespaceObject(); // 53 - default: - break; - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPendingException -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - return v8InternalIsolate->has_pending_exception(); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPendingMessage -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - return v8InternalIsolate->has_pending_message(); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasOwnProperty -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_SYMBOL(v8ValueType)) { - auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); - if (v8MaybeLocalValue.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return false; - } - } - else { - v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); - } - } - if (v8LocalValue->IsObject()) { - V8MaybeBool v8MaybeBool = v8::Just(false); - auto v8LocalObject = v8LocalValue.As(); - if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); - v8MaybeBool = v8LocalObject->HasOwnProperty(v8Context, integerKey); - } - else if (Javet::Converter::IsV8ValueString(jniEnv, key)) { - jstring stringKey = Javet::Converter::ToJavaStringFromV8ValueString(jniEnv, key); - auto v8ValueKey = Javet::Converter::ToV8String(jniEnv, v8Context, stringKey); - v8MaybeBool = v8LocalObject->HasOwnProperty(v8Context, v8ValueKey); - } - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPrivateProperty -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mKey) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsObject()) { - auto v8LocalStringKey = Javet::Converter::ToV8String(jniEnv, v8Context, mKey); - auto v8LocalPrivateKey = v8::Private::ForApi(v8Context->GetIsolate(), v8LocalStringKey); - auto v8MaybeBool = v8LocalValue.As()->HasPrivate(v8Context, v8LocalPrivateKey); - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasScheduledException -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - return v8InternalIsolate->has_scheduled_exception(); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_idleNotificationDeadline -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong deadlineInMillis) { - if (deadlineInMillis > 0) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - v8Context->GetIsolate()->IdleNotificationDeadline(((long)deadlineInMillis) / 1000.0); - } -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_invoke -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mFunctionName, jboolean mResultRequired, jobjectArray mValues) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_SYMBOL(v8ValueType)) { - auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); - if (v8MaybeLocalValue.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); - } - } - if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - auto v8MaybeLocalValue = v8LocalObject->Get(v8Context, Javet::Converter::ToV8String(jniEnv, v8Context, mFunctionName)); - if (v8MaybeLocalValue.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - auto v8Function = v8MaybeLocalValue.ToLocalChecked(); - if (v8Function->IsFunction()) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - V8MaybeLocalValue v8MaybeLocalValueResult; - uint32_t valueCount = mValues == nullptr ? 0 : jniEnv->GetArrayLength(mValues); - if (valueCount > 0) { - auto umValuesPointer = Javet::Converter::ToV8Values(jniEnv, v8Context, mValues); - v8MaybeLocalValueResult = v8Function.As()->Call(v8Context, v8LocalObject, valueCount, umValuesPointer.get()); - } - else { - v8MaybeLocalValueResult = v8Function.As()->Call(v8Context, v8LocalObject, 0, nullptr); - } - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - else if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - } - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isDead -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - return v8Runtime->v8Isolate->IsDead(); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isInUse -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - return v8Runtime->v8Isolate->IsInUse(); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isWeak -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_DATA_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (!v8PersistentDataPointer->IsEmpty()) { - return (jboolean)v8PersistentDataPointer->IsWeak(); - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_lockV8Runtime -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - if (v8Runtime->IsLocked()) { - return false; - } - v8Runtime->Lock(); - return true; -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_lowMemoryNotification -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - v8Context->GetIsolate()->LowMemoryNotification(); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleEvaluate -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jboolean mResultRequired) { - RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalModule->GetStatus() == v8::Module::Status::kInstantiated) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - auto v8MaybeLocalValueResult = v8LocalModule->Evaluate(v8Context); - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { - Javet::Exceptions::ClearJNIException(jniEnv); - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - } - Javet::Exceptions::ClearJNIException(jniEnv); - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetException -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalModule->GetStatus() == v8::Module::Status::kErrored) { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalModule->GetException()); - } - return nullptr; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetNamespace -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalModule->GetModuleNamespace()); -} - -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetScriptId -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - return (jint)v8LocalModule->ScriptId(); -} - -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetStatus -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - return (jint)v8LocalModule->GetStatus(); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_moduleInstantiate -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalModule->GetStatus() == v8::Module::Status::kUninstantiated) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - auto v8MaybeBool = v8LocalModule->InstantiateModule(v8Context, Javet::Callback::JavetModuleResolveCallback); - if (v8TryCatch.HasCaught()) { - Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_promiseGetState -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROMISE(v8ValueType)) { - return (jint)v8LocalValue.As()->State(); - } - return -1; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseCatch -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jlong v8ValueFunctionHandle) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROMISE(v8ValueType)) { - auto v8PersistentFunctionPointer = TO_V8_PERSISTENT_FUNCTION_POINTER(v8ValueFunctionHandle); - auto v8LocalFunction = v8PersistentFunctionPointer->Get(v8Context->GetIsolate()); - auto v8MaybeLocalValueResult = v8LocalValue.As()->Catch(v8Context, v8LocalFunction); - if (v8MaybeLocalValueResult.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseGetResult -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROMISE(v8ValueType)) { - auto v8LocalPromise = v8LocalValue.As(); - if (v8LocalPromise->State() != v8::Promise::PromiseState::kPending) { - auto v8ValueResult = v8LocalPromise->Result(); - if (v8ValueResult.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8ValueResult); - } - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_promiseHasHandler -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROMISE(v8ValueType)) { - return v8LocalValue.As()->HasHandler(); - } - return false; -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_promiseMarkAsHandled -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROMISE(v8ValueType)) { - v8LocalValue.As()->MarkAsHandled(); - } -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseThen -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jlong v8ValueFunctionFulfilledHandle, jlong v8ValueFunctionRejectedHandle) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROMISE(v8ValueType)) { - auto v8PersistentFunctionFulfilledPointer = TO_V8_PERSISTENT_FUNCTION_POINTER(v8ValueFunctionFulfilledHandle); - auto v8LocalFunctionFulfilled = v8PersistentFunctionFulfilledPointer->Get(v8Context->GetIsolate()); - V8MaybeLocalPromise v8MaybeLocalValueResult; - if (v8ValueFunctionRejectedHandle == 0L) { - v8MaybeLocalValueResult = v8LocalValue.As()->Then(v8Context, v8LocalFunctionFulfilled); - } - else { - auto v8PersistentFunctionRejectedPointer = TO_V8_PERSISTENT_FUNCTION_POINTER(v8ValueFunctionRejectedHandle); - auto v8LocalFunctionRejected = v8PersistentFunctionRejectedPointer->Get(v8Context->GetIsolate()); - v8MaybeLocalValueResult = v8LocalValue.As()->Then(v8Context, v8LocalFunctionFulfilled, v8LocalFunctionRejected); - } - if (v8MaybeLocalValueResult.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - else { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseGetPromise -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROMISE(v8ValueType)) { - auto v8LocalPromiseResolver = v8LocalValue.As(); - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalPromiseResolver->GetPromise()); - } - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_promiseReject -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE_WITH_UNIQUE_LOCKER(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROMISE(v8ValueType)) { - auto v8LocalPromiseResolver = v8LocalValue.As(); - auto v8MaybeBool = v8LocalPromiseResolver->Reject(v8Context, Javet::Converter::ToV8Value(jniEnv, v8Context, value)); - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_promiseResolve -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE_WITH_UNIQUE_LOCKER(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROMISE(v8ValueType)) { - auto v8LocalPromiseResolver = v8LocalValue.As(); - auto v8MaybeBool = v8LocalPromiseResolver->Resolve(v8Context, Javet::Converter::ToV8Value(jniEnv, v8Context, value)); - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_promoteScheduledException -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); - if (v8InternalIsolate->has_scheduled_exception()) { - v8InternalIsolate->PromoteScheduledException(); - return true; - } - return false; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_proxyGetHandler -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROXY(v8ValueType)) { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalValue.As()->GetHandler()); - } - return nullptr; -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_proxyGetTarget -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROXY(v8ValueType)) { - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalValue.As()->GetTarget()); - } - return nullptr; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_proxyIsRevoked -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROXY(v8ValueType)) { - return v8LocalValue.As()->IsRevoked(); - } - return false; -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_proxyRevoke -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (IS_V8_PROXY(v8ValueType)) { - v8LocalValue.As()->Revoke(); - } -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_registerGCEpilogueCallback -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - v8Runtime->v8Isolate->AddGCEpilogueCallback(Javet::Callback::JavetGCEpilogueCallback); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_registerGCPrologueCallback -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - v8Runtime->v8Isolate->AddGCPrologueCallback(Javet::Callback::JavetGCPrologueCallback); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_registerV8Runtime -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mV8Runtime) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - v8Runtime->ClearExternalException(jniEnv); - v8Runtime->ClearExternalV8Runtime(jniEnv); - v8Runtime->externalV8Runtime = jniEnv->NewGlobalRef(mV8Runtime); - INCREASE_COUNTER(Javet::Monitor::CounterType::NewGlobalRef); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_removeJNIGlobalRef -(JNIEnv* jniEnv, jobject caller, jlong handle) { - jniEnv->DeleteGlobalRef((jobject)handle); - INCREASE_COUNTER(Javet::Monitor::CounterType::DeleteGlobalRef); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_removeReferenceHandle -(JNIEnv* jniEnv, jobject caller, jlong referenceHandle, jint referenceType) { - auto v8PersistentDataPointer = TO_V8_PERSISTENT_DATA_POINTER(referenceHandle); - v8PersistentDataPointer->Reset(); - delete v8PersistentDataPointer; - INCREASE_COUNTER(Javet::Monitor::CounterType::DeletePersistentReference); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_reportPendingMessages -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - return Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_requestGarbageCollectionForTesting -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jboolean fullGC) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - v8Context->GetIsolate()->RequestGarbageCollectionForTesting(fullGC - ? v8::Isolate::GarbageCollectionType::kFullGarbageCollection - : v8::Isolate::GarbageCollectionType::kMinorGarbageCollection); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_resetV8Context -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mRuntimeOptions) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - v8Runtime->CloseV8Context(); - v8Runtime->CreateV8Context(jniEnv, mRuntimeOptions); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_resetV8Isolate -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mRuntimeOptions) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - v8Runtime->CloseV8Context(); - v8Runtime->CloseV8Isolate(); - v8Runtime->CreateV8Isolate(); - v8Runtime->CreateV8Context(jniEnv, mRuntimeOptions); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_sameValue -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle1, jlong v8ValueHandle2) { - RUNTIME_AND_2_VALUES_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle1, v8ValueHandle2); - return v8LocalValue1->SameValue(v8LocalValue2); -} - -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_scriptRun -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jboolean mResultRequired) { - RUNTIME_AND_SCRIPT_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (!v8LocalScript.IsEmpty()) { - V8TryCatch v8TryCatch(v8Context->GetIsolate()); - auto v8MaybeLocalValueResult = v8LocalScript->Run(v8Context); - if (v8TryCatch.HasCaught()) { - return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); - } - if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { - Javet::Exceptions::ClearJNIException(jniEnv); - return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); - } - } - Javet::Exceptions::ClearJNIException(jniEnv); - return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_set -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jobject value) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - V8MaybeBool v8MaybeBool = v8::Just(false); - auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); - auto v8ValueValue = Javet::Converter::ToV8Value(jniEnv, v8Context, value); - if (IS_V8_ARRAY(v8ValueType)) { - if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); - v8MaybeBool = v8LocalValue.As()->Set(v8Context, integerKey, v8ValueValue); - } - else if (!v8ValueKey.IsEmpty()) { - v8MaybeBool = v8LocalValue.As()->Set(v8Context, v8ValueKey, v8ValueValue); - } - } - else if (!v8ValueKey.IsEmpty()) { - if (IS_V8_MAP(v8ValueType)) { - auto v8MaybeLocalMap = v8LocalValue.As()->Set(v8Context, v8ValueKey, v8ValueValue); - if (v8MaybeLocalMap.IsEmpty()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - return false; - } - return true; - } - else if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); - v8MaybeBool = v8LocalObject->Set(v8Context, integerKey, v8ValueValue); - } - else { - v8MaybeBool = v8LocalObject->Set(v8Context, v8ValueKey, v8ValueValue); - } - } - } - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setAccessor -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject mPropertyName, jobject mContextGetter, jobject mContextSetter) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - V8MaybeBool v8MaybeBool = v8::Just(false); - if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - V8LocalName v8LocalName; - if (Javet::Converter::IsV8ValueString(jniEnv, mPropertyName)) { - v8LocalName = Javet::Converter::ToV8Value(jniEnv, v8Context, mPropertyName).As(); - } - else if (Javet::Converter::IsV8ValueSymbol(jniEnv, mPropertyName)) { - v8LocalName = Javet::Converter::ToV8Value(jniEnv, v8Context, mPropertyName).As(); - } - else { - return false; - } - if (mContextGetter == nullptr) { - v8MaybeBool = v8LocalObject.As()->SetAccessor(v8Context, v8LocalName, nullptr); - } - else { - auto v8LocalArrayContext = v8::Array::New(v8Context->GetIsolate(), 2); - auto javetCallbackContextReferencePointer = new Javet::Callback::JavetCallbackContextReference(jniEnv, mContextGetter); - INCREASE_COUNTER(Javet::Monitor::CounterType::NewJavetCallbackContextReference); - auto v8LocalContextGetterHandle = v8::BigInt::New(v8Context->GetIsolate(), TO_NATIVE_INT_64(javetCallbackContextReferencePointer)); - javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer = - new V8PersistentBigInt(v8Context->GetIsolate(), v8LocalContextGetterHandle); - INCREASE_COUNTER(Javet::Monitor::CounterType::NewPersistentCallbackContextReference); - javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer->SetWeak( - javetCallbackContextReferencePointer, Javet::Callback::JavetCloseWeakCallbackContextHandle, v8::WeakCallbackType::kParameter); - auto maybeResult = v8LocalArrayContext->Set(v8Context, 0, v8LocalContextGetterHandle); - v8::AccessorNameGetterCallback getter = Javet::Callback::JavetPropertyGetterCallback; - v8::AccessorNameSetterCallback setter = nullptr; - if (mContextSetter != nullptr) { - javetCallbackContextReferencePointer = new Javet::Callback::JavetCallbackContextReference(jniEnv, mContextSetter); - INCREASE_COUNTER(Javet::Monitor::CounterType::NewJavetCallbackContextReference); - auto v8LocalContextSetterHandle = v8::BigInt::New(v8Context->GetIsolate(), TO_NATIVE_INT_64(javetCallbackContextReferencePointer)); - javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer = - new V8PersistentBigInt(v8Context->GetIsolate(), v8LocalContextSetterHandle); - INCREASE_COUNTER(Javet::Monitor::CounterType::NewPersistentCallbackContextReference); - javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer->SetWeak( - javetCallbackContextReferencePointer, Javet::Callback::JavetCloseWeakCallbackContextHandle, v8::WeakCallbackType::kParameter); - maybeResult = v8LocalArrayContext->Set(v8Context, 1, v8LocalContextSetterHandle); - setter = Javet::Callback::JavetPropertySetterCallback; - } - v8MaybeBool = v8LocalObject.As()->SetAccessor(v8Context, v8LocalName, getter, setter, v8LocalArrayContext); - } - } - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setPrivateProperty -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mKey, jobject mValue) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsObject()) { - auto v8LocalStringKey = Javet::Converter::ToV8String(jniEnv, v8Context, mKey); - auto v8LocalPrivateKey = v8::Private::ForApi(v8Context->GetIsolate(), v8LocalStringKey); - auto v8LocalPrivateValue = Javet::Converter::ToV8Value(jniEnv, v8Context, mValue); - auto v8MaybeBool = v8LocalValue.As()->SetPrivate(v8Context, v8LocalPrivateKey, v8LocalPrivateValue); - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setProperty -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jobject value) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsObject()) { - V8MaybeBool v8MaybeBool = v8::Just(false); - auto v8LocalObject = v8LocalValue.As(); - auto v8ValueValue = Javet::Converter::ToV8Value(jniEnv, v8Context, value); - if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { - jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); - v8MaybeBool = v8LocalObject->Set(v8Context, integerKey, v8ValueValue); - } - else { - auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); - if (!v8ValueKey.IsEmpty()) { - v8MaybeBool = v8LocalObject->Set(v8Context, v8ValueKey, v8ValueValue); - } - } - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setPrototype -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jlong v8ValueHandlePrototype) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - auto v8PersistentObjectPrototypePointer = TO_V8_PERSISTENT_VALUE_POINTER(v8ValueHandlePrototype); - auto v8LocalObjectPrototype = v8PersistentObjectPrototypePointer->Get(v8Context->GetIsolate()); - auto v8MaybeBool = v8LocalObject->SetPrototype(v8Context, v8LocalObjectPrototype); - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - } - return v8MaybeBool.FromMaybe(false); - } - return false; -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_setWeak -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject objectReference) { - RUNTIME_AND_DATA_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - if (!v8PersistentDataPointer->IsEmpty() && !v8PersistentDataPointer->IsWeak()) { - auto v8ValueReference = new Javet::Callback::V8ValueReference(jniEnv, objectReference); - INCREASE_COUNTER(Javet::Monitor::CounterType::NewWeakCallbackReference); - v8ValueReference->v8PersistentDataPointer = v8PersistentDataPointer; - v8PersistentDataPointer->SetWeak(v8ValueReference, Javet::Callback::JavetCloseWeakDataReference, v8::WeakCallbackType::kParameter); - } -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_strictEquals -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle1, jlong v8ValueHandle2) { - RUNTIME_AND_2_VALUES_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle1, v8ValueHandle2); - return v8LocalValue1->StrictEquals(v8LocalValue2); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_terminateExecution -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - v8Runtime->v8Isolate->TerminateExecution(); -} - -JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_toProtoString -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - V8MaybeLocalString v8MaybeLocalString; - if (v8LocalValue->IsObject()) { - auto v8LocalObject = v8LocalValue.As(); - v8MaybeLocalString = v8LocalObject->ObjectProtoToString(v8Context); - if (v8MaybeLocalString.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - } - V8LocalString v8LocalString = v8MaybeLocalString.IsEmpty() ? V8LocalString() : v8MaybeLocalString.ToLocalChecked(); - return Javet::Converter::ToJavaString(jniEnv, v8Context, v8LocalString); -} - -JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_toString -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { - RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); - V8MaybeLocalString v8MaybeLocalString; - if (!IS_V8_MODULE(v8ValueType) && !IS_V8_SCRIPT(v8ValueType)) { - if (IS_V8_ARRAY(v8ValueType)) { - v8MaybeLocalString = v8LocalValue.As()->ToString(v8Context); - } - else if (IS_V8_MAP(v8ValueType)) { - v8MaybeLocalString = v8LocalValue.As()->ToString(v8Context); - } - else if (IS_V8_SET(v8ValueType)) { - v8MaybeLocalString = v8LocalValue.As()->ToString(v8Context); - } - else if (v8LocalValue->IsObject()) { - v8MaybeLocalString = v8LocalValue.As()->ToString(v8Context); - } - else { - auto v8MaybeLocalObject = v8LocalValue->ToObject(v8Context); - if (!v8MaybeLocalObject.IsEmpty()) { - v8MaybeLocalString = v8MaybeLocalObject.ToLocalChecked()->ToString(v8Context); - } - } - if (v8MaybeLocalString.IsEmpty()) { - if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { - return nullptr; - } - } - } - V8LocalString v8LocalString = v8MaybeLocalString.IsEmpty() ? V8LocalString() : v8MaybeLocalString.ToLocalChecked(); - return Javet::Converter::ToJavaString(jniEnv, v8Context, v8LocalString); -} - -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_unlockV8Runtime -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - if (!v8Runtime->IsLocked()) { - return false; - } - v8Runtime->Unlock(); - return true; -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_unregisterGCEpilogueCallback -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - v8Runtime->v8Isolate->RemoveGCEpilogueCallback(Javet::Callback::JavetGCEpilogueCallback); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_unregisterGCPrologueCallback -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { - auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); - v8Runtime->v8Isolate->RemoveGCPrologueCallback(Javet::Callback::JavetGCPrologueCallback); -} - -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_v8InspectorSend -(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mMessage) { - RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); - char const* umMessage = jniEnv->GetStringUTFChars(mMessage, nullptr); - std::string message(umMessage, jniEnv->GetStringUTFLength(mMessage)); - v8Runtime->v8Inspector->send(message); - jniEnv->ReleaseStringUTFChars(mMessage, umMessage); -} - diff --git a/cpp/jni/com_caoccao_javet_interop_V8Native.h b/cpp/jni/com_caoccao_javet_interop_V8Native.h index e3918d012..aa8ec1621 100644 --- a/cpp/jni/com_caoccao_javet_interop_V8Native.h +++ b/cpp/jni/com_caoccao_javet_interop_V8Native.h @@ -7,14 +7,6 @@ #ifdef __cplusplus extern "C" { #endif -/* - * Class: com_caoccao_javet_interop_V8Native - * Method: add - * Signature: (JJILjava/lang/Object;)V - */ -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_add - (JNIEnv *, jobject, jlong, jlong, jint, jobject); - /* * Class: com_caoccao_javet_interop_V8Native * Method: allowCodeGenerationFromStrings @@ -23,6 +15,38 @@ JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_add JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_allowCodeGenerationFromStrings (JNIEnv *, jobject, jlong, jboolean); +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: arrayBufferCreate + * Signature: (JI)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_arrayBufferCreate__JI + (JNIEnv *, jobject, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: arrayBufferCreate + * Signature: (JLjava/nio/ByteBuffer;)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_arrayBufferCreate__JLjava_nio_ByteBuffer_2 + (JNIEnv *, jobject, jlong, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: arrayCreate + * Signature: (J)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_arrayCreate + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: arrayGetLength + * Signature: (JJI)I + */ +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_arrayGetLength + (JNIEnv *, jobject, jlong, jlong, jint); + /* * Class: com_caoccao_javet_interop_V8Native * Method: await @@ -33,19 +57,19 @@ JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_await /* * Class: com_caoccao_javet_interop_V8Native - * Method: call - * Signature: (JJILjava/lang/Object;Z[Ljava/lang/Object;)Ljava/lang/Object; + * Method: batchArrayGet + * Signature: (JJI[Ljava/lang/Object;II)I */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_call - (JNIEnv *, jobject, jlong, jlong, jint, jobject, jboolean, jobjectArray); +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_batchArrayGet + (JNIEnv *, jobject, jlong, jlong, jint, jobjectArray, jint, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: callAsConstructor - * Signature: (JJI[Ljava/lang/Object;)Ljava/lang/Object; + * Method: batchObjectGet + * Signature: (JJI[Ljava/lang/Object;[Ljava/lang/Object;I)I */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_callAsConstructor - (JNIEnv *, jobject, jlong, jlong, jint, jobjectArray); +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_batchObjectGet + (JNIEnv *, jobject, jlong, jlong, jint, jobjectArray, jobjectArray, jint); /* * Class: com_caoccao_javet_interop_V8Native @@ -79,22 +103,6 @@ JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_cloneV8Value JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_closeV8Runtime (JNIEnv *, jobject, jlong); -/* - * Class: com_caoccao_javet_interop_V8Native - * Method: compile - * Signature: (JLjava/lang/String;[BZLjava/lang/String;IIIZZ)Ljava/lang/Object; - */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_compile - (JNIEnv *, jobject, jlong, jstring, jbyteArray, jboolean, jstring, jint, jint, jint, jboolean, jboolean); - -/* - * Class: com_caoccao_javet_interop_V8Native - * Method: compileFunction - * Signature: (JLjava/lang/String;[BLjava/lang/String;IIIZ[Ljava/lang/String;[Ljava/lang/Object;)Ljava/lang/Object; - */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_compileFunction - (JNIEnv *, jobject, jlong, jstring, jbyteArray, jstring, jint, jint, jint, jboolean, jobjectArray, jobjectArray); - /* * Class: com_caoccao_javet_interop_V8Native * Method: contextGet @@ -143,30 +151,6 @@ JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_createV8Inspector JNIEXPORT jlong JNICALL Java_com_caoccao_javet_interop_V8Native_createV8Runtime (JNIEnv *, jobject, jobject); -/* - * Class: com_caoccao_javet_interop_V8Native - * Method: createV8Value - * Signature: (JILjava/lang/Object;)Ljava/lang/Object; - */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_createV8Value - (JNIEnv *, jobject, jlong, jint, jobject); - -/* - * Class: com_caoccao_javet_interop_V8Native - * Method: delete - * Signature: (JJILjava/lang/Object;)Z - */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_delete - (JNIEnv *, jobject, jlong, jlong, jint, jobject); - -/* - * Class: com_caoccao_javet_interop_V8Native - * Method: deletePrivateProperty - * Signature: (JJILjava/lang/String;)Z - */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_deletePrivateProperty - (JNIEnv *, jobject, jlong, jlong, jint, jstring); - /* * Class: com_caoccao_javet_interop_V8Native * Method: equals @@ -177,11 +161,19 @@ JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_equals /* * Class: com_caoccao_javet_interop_V8Native - * Method: execute - * Signature: (JLjava/lang/String;[BZLjava/lang/String;IIIZZ)Ljava/lang/Object; + * Method: functionCall + * Signature: (JJILjava/lang/Object;Z[Ljava/lang/Object;)Ljava/lang/Object; */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_execute - (JNIEnv *, jobject, jlong, jstring, jbyteArray, jboolean, jstring, jint, jint, jint, jboolean, jboolean); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionCall + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jboolean, jobjectArray); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionCallAsConstructor + * Signature: (JJI[Ljava/lang/Object;)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionCallAsConstructor + (JNIEnv *, jobject, jlong, jlong, jint, jobjectArray); /* * Class: com_caoccao_javet_interop_V8Native @@ -191,6 +183,14 @@ JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_execute JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionCanDiscardCompiled (JNIEnv *, jobject, jlong, jlong, jint); +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionCompile + * Signature: (JLjava/lang/String;[BLjava/lang/String;IIIZ[Ljava/lang/String;[Ljava/lang/Object;)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionCompile + (JNIEnv *, jobject, jlong, jstring, jbyteArray, jstring, jint, jint, jint, jboolean, jobjectArray, jobjectArray); + /* * Class: com_caoccao_javet_interop_V8Native * Method: functionCopyScopeInfoFrom @@ -199,6 +199,14 @@ JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionCanDi JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionCopyScopeInfoFrom (JNIEnv *, jobject, jlong, jlong, jint, jlong, jint); +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionCreate + * Signature: (JLjava/lang/Object;)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionCreate + (JNIEnv *, jobject, jlong, jobject); + /* * Class: com_caoccao_javet_interop_V8Native * Method: functionDiscardCompiled @@ -215,6 +223,14 @@ JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionDisca JNIEXPORT jobjectArray JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetArguments (JNIEnv *, jobject, jlong, jlong, jint); +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionGetCachedData + * Signature: (JJI)[B + */ +JNIEXPORT jbyteArray JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetCachedData + (JNIEnv *, jobject, jlong, jlong, jint); + /* * Class: com_caoccao_javet_interop_V8Native * Method: functionGetContext @@ -223,6 +239,30 @@ JNIEXPORT jobjectArray JNICALL Java_com_caoccao_javet_interop_V8Native_functionG JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetContext (JNIEnv *, jobject, jlong, jlong, jint); +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionGetInternalProperties + * Signature: (JJI)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetInternalProperties + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionGetJSFunctionType + * Signature: (JJI)I + */ +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetJSFunctionType + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionGetJSScopeType + * Signature: (JJI)I + */ +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetJSScopeType + (JNIEnv *, jobject, jlong, jlong, jint); + /* * Class: com_caoccao_javet_interop_V8Native * Method: functionGetScopeInfos @@ -233,370 +273,658 @@ JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetSco /* * Class: com_caoccao_javet_interop_V8Native - * Method: functionGetScriptSource - * Signature: (JJI)Ljava/lang/Object; + * Method: functionGetScriptSource + * Signature: (JJI)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetScriptSource + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionGetSourceCode + * Signature: (JJI)Ljava/lang/String; + */ +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetSourceCode + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionIsCompiled + * Signature: (JJI)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionIsCompiled + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionIsWrapped + * Signature: (JJI)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionIsWrapped + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionSetContext + * Signature: (JJILjava/lang/Object;)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetContext + (JNIEnv *, jobject, jlong, jlong, jint, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionSetScriptSource + * Signature: (JJILjava/lang/Object;Z)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetScriptSource + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jboolean); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: functionSetSourceCode + * Signature: (JJILjava/lang/String;Z)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetSourceCode + (JNIEnv *, jobject, jlong, jlong, jint, jstring, jboolean); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: getGlobalObject + * Signature: (J)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getGlobalObject + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: getInternalStatistic + * Signature: ()[J + */ +JNIEXPORT jlongArray JNICALL Java_com_caoccao_javet_interop_V8Native_getInternalStatistic + (JNIEnv *, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: getV8HeapSpaceStatistics + * Signature: (JI)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8HeapSpaceStatistics + (JNIEnv *, jobject, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: getV8HeapStatistics + * Signature: (J)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8HeapStatistics + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: getV8SharedMemoryStatistics + * Signature: ()Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8SharedMemoryStatistics + (JNIEnv *, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: getVersion + * Signature: ()Ljava/lang/String; + */ +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_getVersion + (JNIEnv *, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: hasInternalType + * Signature: (JJI)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasInternalType + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: hasPendingException + * Signature: (J)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPendingException + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: hasPendingMessage + * Signature: (J)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPendingMessage + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: hasScheduledException + * Signature: (J)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasScheduledException + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: idleNotificationDeadline + * Signature: (JJ)V + */ +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_idleNotificationDeadline + (JNIEnv *, jobject, jlong, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: isDead + * Signature: (J)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isDead + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: isInUse + * Signature: (J)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isInUse + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: isWeak + * Signature: (JJI)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isWeak + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: lockV8Runtime + * Signature: (J)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_lockV8Runtime + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: lowMemoryNotification + * Signature: (J)V + */ +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_lowMemoryNotification + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapCreate + * Signature: (J)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_mapCreate + (JNIEnv *, jobject, jlong); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapDelete + * Signature: (JJILjava/lang/Object;)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapDelete + (JNIEnv *, jobject, jlong, jlong, jint, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapGet + * Signature: (JJILjava/lang/Object;)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_mapGet + (JNIEnv *, jobject, jlong, jlong, jint, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapGetBoolean + * Signature: (JJILjava/lang/Object;[Z)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetBoolean + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jbooleanArray); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapGetDouble + * Signature: (JJILjava/lang/Object;[Z)D + */ +JNIEXPORT jdouble JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetDouble + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jbooleanArray); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapGetInteger + * Signature: (JJILjava/lang/Object;[Z)I + */ +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetInteger + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jbooleanArray); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapGetLong + * Signature: (JJILjava/lang/Object;[Z)J + */ +JNIEXPORT jlong JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetLong + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jbooleanArray); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapGetSize + * Signature: (JJI)I + */ +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetSize + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapGetString + * Signature: (JJILjava/lang/Object;)Ljava/lang/String; + */ +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetString + (JNIEnv *, jobject, jlong, jlong, jint, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapHas + * Signature: (JJILjava/lang/Object;)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapHas + (JNIEnv *, jobject, jlong, jlong, jint, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapSet + * Signature: (JJI[Ljava/lang/Object;)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSet + (JNIEnv *, jobject, jlong, jlong, jint, jobjectArray); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: mapSetBoolean + * Signature: (JJILjava/lang/Object;Z)Z */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetScriptSource - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetBoolean + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jboolean); /* * Class: com_caoccao_javet_interop_V8Native - * Method: functionGetSourceCode - * Signature: (JJI)Ljava/lang/String; + * Method: mapSetDouble + * Signature: (JJILjava/lang/Object;D)Z */ -JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetSourceCode - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetDouble + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jdouble); /* * Class: com_caoccao_javet_interop_V8Native - * Method: functionIsCompiled - * Signature: (JJI)Z + * Method: mapSetInteger + * Signature: (JJILjava/lang/Object;I)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionIsCompiled - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetInteger + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: functionIsWrapped - * Signature: (JJI)Z + * Method: mapSetLong + * Signature: (JJILjava/lang/Object;J)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionIsWrapped - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetLong + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jlong); /* * Class: com_caoccao_javet_interop_V8Native - * Method: functionSetContext + * Method: mapSetNull * Signature: (JJILjava/lang/Object;)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetContext +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetNull (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: functionSetScriptSource - * Signature: (JJILjava/lang/Object;Z)Z + * Method: mapSetString + * Signature: (JJILjava/lang/Object;Ljava/lang/String;)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetScriptSource - (JNIEnv *, jobject, jlong, jlong, jint, jobject, jboolean); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetString + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jstring); /* * Class: com_caoccao_javet_interop_V8Native - * Method: functionSetSourceCode - * Signature: (JJILjava/lang/String;Z)Z + * Method: mapSetUndefined + * Signature: (JJILjava/lang/Object;)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetSourceCode - (JNIEnv *, jobject, jlong, jlong, jint, jstring, jboolean); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetUndefined + (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: get - * Signature: (JJILjava/lang/Object;)Ljava/lang/Object; + * Method: moduleCompile + * Signature: (JLjava/lang/String;[BZLjava/lang/String;IIIZZ)Ljava/lang/Object; */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_get - (JNIEnv *, jobject, jlong, jlong, jint, jobject); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleCompile + (JNIEnv *, jobject, jlong, jstring, jbyteArray, jboolean, jstring, jint, jint, jint, jboolean, jboolean); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getCachedData - * Signature: (JJI)[B + * Method: moduleEvaluate + * Signature: (JJIZ)Ljava/lang/Object; */ -JNIEXPORT jbyteArray JNICALL Java_com_caoccao_javet_interop_V8Native_getCachedData - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleEvaluate + (JNIEnv *, jobject, jlong, jlong, jint, jboolean); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getGlobalObject - * Signature: (J)Ljava/lang/Object; + * Method: moduleExecute + * Signature: (JLjava/lang/String;[BZLjava/lang/String;IIIZ)Ljava/lang/Object; */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getGlobalObject - (JNIEnv *, jobject, jlong); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleExecute + (JNIEnv *, jobject, jlong, jstring, jbyteArray, jboolean, jstring, jint, jint, jint, jboolean); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getIdentityHash - * Signature: (JJI)I + * Method: moduleGetCachedData + * Signature: (JJI)[B */ -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getIdentityHash +JNIEXPORT jbyteArray JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetCachedData (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getInternalProperties + * Method: moduleGetException * Signature: (JJI)Ljava/lang/Object; */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getInternalProperties +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetException (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getInternalStatistic - * Signature: ()[J + * Method: moduleGetNamespace + * Signature: (JJI)Ljava/lang/Object; */ -JNIEXPORT jlongArray JNICALL Java_com_caoccao_javet_interop_V8Native_getInternalStatistic - (JNIEnv *, jobject); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetNamespace + (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getJSFunctionType + * Method: moduleGetScriptId * Signature: (JJI)I */ -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getJSFunctionType +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetScriptId (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getJSScopeType + * Method: moduleGetStatus * Signature: (JJI)I */ -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getJSScopeType +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetStatus (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getLength - * Signature: (JJI)I + * Method: moduleInstantiate + * Signature: (JJI)Z */ -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getLength +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_moduleInstantiate (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getOwnPropertyNames - * Signature: (JJI)Ljava/lang/Object; + * Method: objectCreate + * Signature: (J)Ljava/lang/Object; */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getOwnPropertyNames - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectCreate + (JNIEnv *, jobject, jlong); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getPrivateProperty - * Signature: (JJILjava/lang/String;)Ljava/lang/Object; + * Method: objectDelete + * Signature: (JJILjava/lang/Object;)Z */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getPrivateProperty +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectDelete + (JNIEnv *, jobject, jlong, jlong, jint, jobject); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: objectDeletePrivateProperty + * Signature: (JJILjava/lang/String;)Z + */ +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectDeletePrivateProperty (JNIEnv *, jobject, jlong, jlong, jint, jstring); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getProperty + * Method: objectGet * Signature: (JJILjava/lang/Object;)Ljava/lang/Object; */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getProperty +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGet (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getPropertyNames - * Signature: (JJI)Ljava/lang/Object; + * Method: objectGetBoolean + * Signature: (JJILjava/lang/Object;[Z)Z */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getPropertyNames - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetBoolean + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jbooleanArray); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getPrototype - * Signature: (JJI)Ljava/lang/Object; + * Method: objectGetDouble + * Signature: (JJILjava/lang/Object;[Z)D */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getPrototype - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jdouble JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetDouble + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jbooleanArray); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getSize + * Method: objectGetIdentityHash * Signature: (JJI)I */ -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_getSize +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetIdentityHash (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getV8HeapSpaceStatistics - * Signature: (JI)Ljava/lang/Object; + * Method: objectGetInteger + * Signature: (JJILjava/lang/Object;[Z)I */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8HeapSpaceStatistics - (JNIEnv *, jobject, jlong, jint); +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetInteger + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jbooleanArray); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getV8HeapStatistics - * Signature: (J)Ljava/lang/Object; + * Method: objectGetLong + * Signature: (JJILjava/lang/Object;[Z)J */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8HeapStatistics - (JNIEnv *, jobject, jlong); +JNIEXPORT jlong JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetLong + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jbooleanArray); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getV8SharedMemoryStatistics - * Signature: ()Ljava/lang/Object; + * Method: objectGetOwnPropertyNames + * Signature: (JJI)Ljava/lang/Object; */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8SharedMemoryStatistics - (JNIEnv *, jobject); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetOwnPropertyNames + (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: getVersion - * Signature: ()Ljava/lang/String; + * Method: objectGetPrivateProperty + * Signature: (JJILjava/lang/String;)Ljava/lang/Object; */ -JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_getVersion - (JNIEnv *, jobject); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetPrivateProperty + (JNIEnv *, jobject, jlong, jlong, jint, jstring); /* * Class: com_caoccao_javet_interop_V8Native - * Method: has - * Signature: (JJILjava/lang/Object;)Z + * Method: objectGetProperty + * Signature: (JJILjava/lang/Object;)Ljava/lang/Object; */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_has +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetProperty (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: hasInternalType - * Signature: (JJI)Z + * Method: objectGetPropertyNames + * Signature: (JJI)Ljava/lang/Object; */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasInternalType +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetPropertyNames (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: hasOwnProperty - * Signature: (JJILjava/lang/Object;)Z + * Method: objectGetPrototype + * Signature: (JJI)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetPrototype + (JNIEnv *, jobject, jlong, jlong, jint); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: objectGetString + * Signature: (JJILjava/lang/Object;)Ljava/lang/String; */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasOwnProperty +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetString (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: hasPendingException - * Signature: (J)Z + * Method: objectHas + * Signature: (JJILjava/lang/Object;)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPendingException - (JNIEnv *, jobject, jlong); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectHas + (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: hasPendingMessage - * Signature: (J)Z + * Method: objectHasOwnProperty + * Signature: (JJILjava/lang/Object;)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPendingMessage - (JNIEnv *, jobject, jlong); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectHasOwnProperty + (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: hasPrivateProperty + * Method: objectHasPrivateProperty * Signature: (JJILjava/lang/String;)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPrivateProperty +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectHasPrivateProperty (JNIEnv *, jobject, jlong, jlong, jint, jstring); /* * Class: com_caoccao_javet_interop_V8Native - * Method: hasScheduledException - * Signature: (J)Z + * Method: objectInvoke + * Signature: (JJILjava/lang/String;Z[Ljava/lang/Object;)Ljava/lang/Object; */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasScheduledException - (JNIEnv *, jobject, jlong); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectInvoke + (JNIEnv *, jobject, jlong, jlong, jint, jstring, jboolean, jobjectArray); /* * Class: com_caoccao_javet_interop_V8Native - * Method: idleNotificationDeadline - * Signature: (JJ)V + * Method: objectSet + * Signature: (JJI[Ljava/lang/Object;)Z */ -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_idleNotificationDeadline - (JNIEnv *, jobject, jlong, jlong); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSet + (JNIEnv *, jobject, jlong, jlong, jint, jobjectArray); /* * Class: com_caoccao_javet_interop_V8Native - * Method: invoke - * Signature: (JJILjava/lang/String;Z[Ljava/lang/Object;)Ljava/lang/Object; + * Method: objectSetAccessor + * Signature: (JJILjava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)Z */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_invoke - (JNIEnv *, jobject, jlong, jlong, jint, jstring, jboolean, jobjectArray); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetAccessor + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jobject, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: isDead - * Signature: (J)Z + * Method: objectSetBoolean + * Signature: (JJILjava/lang/Object;Z)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isDead - (JNIEnv *, jobject, jlong); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetBoolean + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jboolean); /* * Class: com_caoccao_javet_interop_V8Native - * Method: isInUse - * Signature: (J)Z + * Method: objectSetDouble + * Signature: (JJILjava/lang/Object;D)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isInUse - (JNIEnv *, jobject, jlong); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetDouble + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jdouble); /* * Class: com_caoccao_javet_interop_V8Native - * Method: isWeak - * Signature: (JJI)Z + * Method: objectSetInteger + * Signature: (JJILjava/lang/Object;I)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isWeak - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetInteger + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: lockV8Runtime - * Signature: (J)Z + * Method: objectSetLong + * Signature: (JJILjava/lang/Object;J)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_lockV8Runtime - (JNIEnv *, jobject, jlong); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetLong + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jlong); /* * Class: com_caoccao_javet_interop_V8Native - * Method: lowMemoryNotification - * Signature: (J)V + * Method: objectSetNull + * Signature: (JJILjava/lang/Object;)Z */ -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_lowMemoryNotification - (JNIEnv *, jobject, jlong); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetNull + (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: moduleEvaluate - * Signature: (JJIZ)Ljava/lang/Object; + * Method: objectSetPrivateProperty + * Signature: (JJILjava/lang/String;Ljava/lang/Object;)Z */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleEvaluate - (JNIEnv *, jobject, jlong, jlong, jint, jboolean); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetPrivateProperty + (JNIEnv *, jobject, jlong, jlong, jint, jstring, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: moduleGetException - * Signature: (JJI)Ljava/lang/Object; + * Method: objectSetProperty + * Signature: (JJILjava/lang/Object;Ljava/lang/Object;)Z */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetException - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetProperty + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: moduleGetNamespace - * Signature: (JJI)Ljava/lang/Object; + * Method: objectSetPrototype + * Signature: (JJIJ)Z */ -JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetNamespace - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetPrototype + (JNIEnv *, jobject, jlong, jlong, jint, jlong); /* * Class: com_caoccao_javet_interop_V8Native - * Method: moduleGetScriptId - * Signature: (JJI)I + * Method: objectSetString + * Signature: (JJILjava/lang/Object;Ljava/lang/String;)Z */ -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetScriptId - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetString + (JNIEnv *, jobject, jlong, jlong, jint, jobject, jstring); /* * Class: com_caoccao_javet_interop_V8Native - * Method: moduleGetStatus - * Signature: (JJI)I + * Method: objectSetUndefined + * Signature: (JJILjava/lang/Object;)Z */ -JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetStatus - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetUndefined + (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: moduleInstantiate - * Signature: (JJI)Z + * Method: objectToProtoString + * Signature: (JJI)Ljava/lang/String; */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_moduleInstantiate +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_objectToProtoString (JNIEnv *, jobject, jlong, jlong, jint); /* @@ -607,6 +935,14 @@ JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_moduleInstant JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseCatch (JNIEnv *, jobject, jlong, jlong, jint, jlong); +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: promiseCreate + * Signature: (J)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseCreate + (JNIEnv *, jobject, jlong); + /* * Class: com_caoccao_javet_interop_V8Native * Method: promiseGetPromise @@ -679,6 +1015,14 @@ JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseThen JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_promoteScheduledException (JNIEnv *, jobject, jlong); +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: proxyCreate + * Signature: (JLjava/lang/Object;)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_proxyCreate + (JNIEnv *, jobject, jlong, jobject); + /* * Class: com_caoccao_javet_interop_V8Native * Method: proxyGetHandler @@ -791,6 +1135,30 @@ JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_resetV8Isolate JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_sameValue (JNIEnv *, jobject, jlong, jlong, jlong); +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: scriptCompile + * Signature: (JLjava/lang/String;[BZLjava/lang/String;IIIZZ)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_scriptCompile + (JNIEnv *, jobject, jlong, jstring, jbyteArray, jboolean, jstring, jint, jint, jint, jboolean, jboolean); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: scriptExecute + * Signature: (JLjava/lang/String;[BZLjava/lang/String;IIIZ)Ljava/lang/Object; + */ +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_scriptExecute + (JNIEnv *, jobject, jlong, jstring, jbyteArray, jboolean, jstring, jint, jint, jint, jboolean); + +/* + * Class: com_caoccao_javet_interop_V8Native + * Method: scriptGetCachedData + * Signature: (JJI)[B + */ +JNIEXPORT jbyteArray JNICALL Java_com_caoccao_javet_interop_V8Native_scriptGetCachedData + (JNIEnv *, jobject, jlong, jlong, jint); + /* * Class: com_caoccao_javet_interop_V8Native * Method: scriptRun @@ -801,43 +1169,43 @@ JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_scriptRun /* * Class: com_caoccao_javet_interop_V8Native - * Method: set - * Signature: (JJILjava/lang/Object;Ljava/lang/Object;)Z + * Method: setAdd + * Signature: (JJILjava/lang/Object;)V */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_set - (JNIEnv *, jobject, jlong, jlong, jint, jobject, jobject); +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_setAdd + (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: setAccessor - * Signature: (JJILjava/lang/Object;Ljava/lang/Object;Ljava/lang/Object;)Z + * Method: setCreate + * Signature: (J)Ljava/lang/Object; */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setAccessor - (JNIEnv *, jobject, jlong, jlong, jint, jobject, jobject, jobject); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_setCreate + (JNIEnv *, jobject, jlong); /* * Class: com_caoccao_javet_interop_V8Native - * Method: setPrivateProperty - * Signature: (JJILjava/lang/String;Ljava/lang/Object;)Z + * Method: setDelete + * Signature: (JJILjava/lang/Object;)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setPrivateProperty - (JNIEnv *, jobject, jlong, jlong, jint, jstring, jobject); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setDelete + (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native - * Method: setProperty - * Signature: (JJILjava/lang/Object;Ljava/lang/Object;)Z + * Method: setGetSize + * Signature: (JJI)I */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setProperty - (JNIEnv *, jobject, jlong, jlong, jint, jobject, jobject); +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_setGetSize + (JNIEnv *, jobject, jlong, jlong, jint); /* * Class: com_caoccao_javet_interop_V8Native - * Method: setPrototype - * Signature: (JJIJ)Z + * Method: setHas + * Signature: (JJILjava/lang/Object;)Z */ -JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setPrototype - (JNIEnv *, jobject, jlong, jlong, jint, jlong); +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setHas + (JNIEnv *, jobject, jlong, jlong, jint, jobject); /* * Class: com_caoccao_javet_interop_V8Native @@ -857,19 +1225,19 @@ JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_strictEquals /* * Class: com_caoccao_javet_interop_V8Native - * Method: terminateExecution - * Signature: (J)V + * Method: symbolCreate + * Signature: (JLjava/lang/String;)Ljava/lang/Object; */ -JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_terminateExecution - (JNIEnv *, jobject, jlong); +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_symbolCreate + (JNIEnv *, jobject, jlong, jstring); /* * Class: com_caoccao_javet_interop_V8Native - * Method: toProtoString - * Signature: (JJI)Ljava/lang/String; + * Method: terminateExecution + * Signature: (J)V */ -JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_toProtoString - (JNIEnv *, jobject, jlong, jlong, jint); +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_terminateExecution + (JNIEnv *, jobject, jlong); /* * Class: com_caoccao_javet_interop_V8Native diff --git a/cpp/jni/javet_callbacks.cpp b/cpp/jni/javet_callbacks.cpp index 6bc836721..869857e3d 100644 --- a/cpp/jni/javet_callbacks.cpp +++ b/cpp/jni/javet_callbacks.cpp @@ -73,7 +73,7 @@ namespace Javet { jclassV8FunctionCallback = FIND_CLASS(jniEnv, "com/caoccao/javet/interop/callback/V8FunctionCallback"); jmethodIDV8FunctionCallbackReceiveCallback = jniEnv->GetStaticMethodID(jclassV8FunctionCallback, "receiveCallback", - "(Lcom/caoccao/javet/interop/V8Runtime;Lcom/caoccao/javet/interop/callback/JavetCallbackContext;Lcom/caoccao/javet/values/V8Value;Lcom/caoccao/javet/values/reference/V8ValueArray;)Lcom/caoccao/javet/values/V8Value;"); + "(Lcom/caoccao/javet/interop/V8Runtime;Lcom/caoccao/javet/interop/callback/JavetCallbackContext;Lcom/caoccao/javet/values/V8Value;[Lcom/caoccao/javet/values/V8Value;)Lcom/caoccao/javet/values/V8Value;"); jclassV8Runtime = FIND_CLASS(jniEnv, "com/caoccao/javet/interop/V8Runtime"); jmethodIDV8RuntimeGetCallbackContext = jniEnv->GetMethodID(jclassV8Runtime, "getCallbackContext", "(J)Lcom/caoccao/javet/interop/callback/JavetCallbackContext;"); @@ -299,7 +299,7 @@ namespace Javet { jobject callbackContext = jniEnv->CallObjectMethod(externalV8Runtime, jmethodIDV8RuntimeGetCallbackContext, TO_JAVA_LONG(this)); jboolean isReturnResult = jniEnv->CallBooleanMethod(callbackContext, jmethodIDJavetCallbackContextIsReturnResult); jboolean isThisObjectRequired = jniEnv->CallBooleanMethod(callbackContext, jmethodIDJavetCallbackContextIsThisObjectRequired); - jobject externalArgs = Javet::Converter::ToExternalV8ValueArray(jniEnv, v8Runtime, v8Context, args); + jobjectArray externalArgs = Javet::Converter::ToExternalV8ValueArray(jniEnv, v8Runtime, v8Context, args); jobject thisObject = isThisObjectRequired ? Javet::Converter::ToExternalV8Value(jniEnv, v8Runtime, v8Context, args.This()) : nullptr; jobject mResult = jniEnv->CallStaticObjectMethod( jclassV8FunctionCallback, @@ -310,6 +310,7 @@ namespace Javet { externalArgs); DELETE_LOCAL_REF(jniEnv, thisObject); DELETE_LOCAL_REF(jniEnv, externalArgs); + DELETE_LOCAL_REF(jniEnv, callbackContext); if (jniEnv->ExceptionCheck()) { if (mResult != nullptr) { jniEnv->CallStaticVoidMethod(jclassJavetResourceUtils, jmethodIDJavetResourceUtilsSafeClose, mResult); @@ -367,6 +368,7 @@ namespace Javet { thisObject, nullptr); DELETE_LOCAL_REF(jniEnv, thisObject); + DELETE_LOCAL_REF(jniEnv, callbackContext); if (jniEnv->ExceptionCheck()) { Javet::Exceptions::ThrowV8Exception(jniEnv, v8Context, "Uncaught JavaError in property getter callback"); } @@ -408,8 +410,8 @@ namespace Javet { } else { V8ContextScope v8ContextScope(v8Context); - auto v8Array = v8::Array::New(v8Context->GetIsolate(), 1); - auto maybeResult = v8Array->Set(v8Context, 0, propertyValue); + auto v8LocalArray = v8::Array::New(v8Context->GetIsolate(), 1); + auto maybeResult = v8LocalArray->Set(v8Context, 0, propertyValue); if (maybeResult.IsNothing()) { Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); } @@ -418,7 +420,7 @@ namespace Javet { jobject callbackContext = jniEnv->CallObjectMethod(externalV8Runtime, jmethodIDV8RuntimeGetCallbackContext, TO_JAVA_LONG(this)); jboolean isThisObjectRequired = jniEnv->CallBooleanMethod(callbackContext, jmethodIDJavetCallbackContextIsThisObjectRequired); jobject thisObject = isThisObjectRequired ? Javet::Converter::ToExternalV8Value(jniEnv, v8Runtime, v8Context, args.This()) : nullptr; - jobject mArguments = Javet::Converter::ToExternalV8Value(jniEnv, v8Runtime, v8Context, v8Array); + jobjectArray mArguments = Javet::Converter::ToExternalV8ValueArray(jniEnv, v8Runtime, v8Context, v8LocalArray); jobject mResult = jniEnv->CallStaticObjectMethod( jclassV8FunctionCallback, jmethodIDV8FunctionCallbackReceiveCallback, @@ -428,6 +430,7 @@ namespace Javet { mArguments); DELETE_LOCAL_REF(jniEnv, thisObject); DELETE_LOCAL_REF(jniEnv, mArguments); + DELETE_LOCAL_REF(jniEnv, callbackContext); if (jniEnv->ExceptionCheck()) { Javet::Exceptions::ThrowV8Exception(jniEnv, v8Context, "Uncaught JavaError in property setter callback"); } diff --git a/cpp/jni/javet_converter.cpp b/cpp/jni/javet_converter.cpp index 4c6b90c65..257e3e4a4 100644 --- a/cpp/jni/javet_converter.cpp +++ b/cpp/jni/javet_converter.cpp @@ -40,6 +40,8 @@ namespace Javet { // Primitive + jclass jclassV8Value; + jclass jclassV8ValueBigInteger; jmethodID jmethodIDV8ValueBigIntegerConstructor; jmethodID jmethodIDV8ValueBigIntegerGetLongArray; @@ -339,6 +341,8 @@ namespace Javet { // Primitive + jclassV8Value = FIND_CLASS(jniEnv, "com/caoccao/javet/values/V8Value"); + jclassV8ValueBigInteger = FIND_CLASS(jniEnv, "com/caoccao/javet/values/primitive/V8ValueBigInteger"); jmethodIDV8ValueBigIntegerConstructor = jniEnv->GetMethodID(jclassV8ValueBigInteger, "", "(Lcom/caoccao/javet/interop/V8Runtime;I[J)V"); jmethodIDV8ValueBigIntegerGetLongArray = jniEnv->GetMethodID(jclassV8ValueBigInteger, "getLongArray", "()[J"); @@ -853,24 +857,71 @@ namespace Javet { v8Value); } - jobject ToExternalV8ValueArray( + jobjectArray ToExternalV8ValueArray( JNIEnv* jniEnv, V8Runtime* v8Runtime, const V8LocalContext& v8Context, const v8::FunctionCallbackInfo& args) noexcept { + jobjectArray v8ValueArray = nullptr; int argLength = args.Length(); if (argLength > 0) { - auto v8Array = v8::Array::New(v8Context->GetIsolate(), argLength); + // TODO: Memory leak might take place. + v8ValueArray = jniEnv->NewObjectArray(argLength, jclassV8Value, nullptr); for (int i = 0; i < argLength; ++i) { - auto v8MaybeBool = v8Array->Set(v8Context, i, args[i]); - if (v8MaybeBool.IsNothing()) { - Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); - return nullptr; + jniEnv->SetObjectArrayElement(v8ValueArray, i, ToExternalV8Value(jniEnv, v8Runtime, v8Context, args[i])); + } + } + return v8ValueArray; + } + + jobjectArray ToExternalV8ValueArray( + JNIEnv* jniEnv, + V8Runtime* v8Runtime, + const V8LocalContext& v8Context, + const V8LocalArray& v8LocalArray) noexcept { + int length = v8LocalArray->Length(); + // TODO: Memory leak might take place. + auto v8ValueArray = jniEnv->NewObjectArray(length, jclassV8Value, nullptr); + ToExternalV8ValueArray( + jniEnv, + v8Runtime, + v8Context, + v8LocalArray, + v8ValueArray, + 0, + length); + return v8ValueArray; + } + + int ToExternalV8ValueArray( + JNIEnv* jniEnv, + V8Runtime* v8Runtime, + const V8LocalContext& v8Context, + const V8LocalArray& v8LocalArray, + jobjectArray v8Values, + const int startIndex, + const int endIndex) noexcept { + int arrayLength = v8LocalArray->Length(); + int actualEndIndex = endIndex > arrayLength ? arrayLength : endIndex; + int actualLength = actualEndIndex - startIndex; + if (startIndex >= 0 && actualLength > 0) { + for (int i = 0; i < actualLength; ++i) { + auto v8MaybeLocalValue = v8LocalArray->Get(v8Context, i + startIndex); + V8LocalValue v8LocalValue; + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return i; + } + } + else { + v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); } + jniEnv->SetObjectArrayElement( + v8Values, i, ToExternalV8Value(jniEnv, v8Runtime, v8Context, v8LocalValue)); } - return ToExternalV8Value(jniEnv, v8Runtime, v8Context, v8Array); + return actualLength; } - return nullptr; + return 0; } jobject ToExternalV8ValueGlobalObject( diff --git a/cpp/jni/javet_converter.h b/cpp/jni/javet_converter.h index 4ec8b05fe..15db65e71 100644 --- a/cpp/jni/javet_converter.h +++ b/cpp/jni/javet_converter.h @@ -160,12 +160,27 @@ namespace Javet { const V8LocalContext& v8Context, const V8LocalValue& v8Value) noexcept; - jobject ToExternalV8ValueArray( + jobjectArray ToExternalV8ValueArray( JNIEnv* jniEnv, V8Runtime* v8Runtime, const V8LocalContext& v8Context, const v8::FunctionCallbackInfo& args) noexcept; + jobjectArray ToExternalV8ValueArray( + JNIEnv* jniEnv, + V8Runtime* v8Runtime, + const V8LocalContext& v8Context, + const V8LocalArray& v8LocalArray) noexcept; + + int ToExternalV8ValueArray( + JNIEnv* jniEnv, + V8Runtime* v8Runtime, + const V8LocalContext& v8Context, + const V8LocalArray& v8LocalArray, + jobjectArray v8Values, + const int startIndex, + const int endIndex) noexcept; + jobject ToExternalV8ValueGlobalObject( JNIEnv* jniEnv, const V8Runtime* v8Runtime) noexcept; diff --git a/cpp/jni/javet_jni.h b/cpp/jni/javet_jni.h new file mode 100644 index 000000000..f4109545d --- /dev/null +++ b/cpp/jni/javet_jni.h @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "com_caoccao_javet_interop_V8Native.h" +#include "com_caoccao_javet_interop_NodeNative.h" +#include "javet_callbacks.h" +#include "javet_converter.h" +#include "javet_enums.h" +#include "javet_exceptions.h" +#include "javet_inspector.h" +#include "javet_monitor.h" +#include "javet_logging.h" +#include "javet_native.h" +#include "javet_node.h" +#include "javet_v8.h" +#include "javet_v8_runtime.h" diff --git a/cpp/jni/javet_jni_array.cpp b/cpp/jni/javet_jni_array.cpp new file mode 100644 index 000000000..b6d7572c4 --- /dev/null +++ b/cpp/jni/javet_jni_array.cpp @@ -0,0 +1,57 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_arrayCreate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8LocalArray = v8::Array::New(v8Context->GetIsolate()); + if (!v8LocalArray.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalArray); + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_arrayGetLength +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_ARRAY(v8ValueType)) { + return (jint)v8LocalValue.As()->Length(); + } + if (v8LocalValue->IsTypedArray()) { + return (jint)v8LocalValue.As()->Length(); + } + return 0; +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_batchArrayGet +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, + jobjectArray v8Values, jint startIndex, jint endIndex) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_ARRAY(v8ValueType) || IS_V8_ARGUMENTS(v8ValueType) || v8LocalValue->IsTypedArray()) { + return Javet::Converter::ToExternalV8ValueArray( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue.As(), + v8Values, + startIndex, + endIndex); + } + return 0; +} diff --git a/cpp/jni/javet_jni_array_buffer.cpp b/cpp/jni/javet_jni_array_buffer.cpp new file mode 100644 index 000000000..521af2a83 --- /dev/null +++ b/cpp/jni/javet_jni_array_buffer.cpp @@ -0,0 +1,45 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_arrayBufferCreate__JI +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jint length) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + if (length >= 0) { + auto v8LocalArrayBuffer = v8::ArrayBuffer::New(v8Context->GetIsolate(), length); + if (!v8LocalArrayBuffer.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalArrayBuffer); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_arrayBufferCreate__JLjava_nio_ByteBuffer_2 +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mByteBuffer) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + std::unique_ptr v8BackingStorePointer = v8::ArrayBuffer::NewBackingStore( + jniEnv->GetDirectBufferAddress(mByteBuffer), + static_cast(jniEnv->GetDirectBufferCapacity(mByteBuffer)), + [](void*, size_t, void*) {}, + nullptr); + auto v8LocalArrayBuffer = v8::ArrayBuffer::New(v8Context->GetIsolate(), std::move(v8BackingStorePointer)); + if (!v8LocalArrayBuffer.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalArrayBuffer); + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} diff --git a/cpp/jni/javet_jni_context.cpp b/cpp/jni/javet_jni_context.cpp new file mode 100644 index 000000000..9ceb55371 --- /dev/null +++ b/cpp/jni/javet_jni_context.cpp @@ -0,0 +1,81 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_contextGet +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jint index) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_CONTEXT(v8ValueType)) { + V8LocalContext v8ContextValue = v8LocalValue.As(); + V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); + if (index >= 0 && index < v8InternalContext.length()) { + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + auto v8InternalObject = v8InternalContext.get(index); + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8InternalObject); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_contextGetLength +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_CONTEXT(v8ValueType)) { + V8LocalContext v8ContextValue = v8LocalValue.As(); + V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); + return v8InternalContext.length(); + } + return 0; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_contextIsContextType +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jint contextTypeId) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_CONTEXT(v8ValueType)) { + V8LocalContext v8ContextValue = v8LocalValue.As(); + V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); + using namespace Javet::Enums::V8ContextType; + switch (contextTypeId) { + case Await: return v8InternalContext.IsAwaitContext(); // 0 + case Block: return v8InternalContext.IsBlockContext(); // 1 + case Catch: return v8InternalContext.IsCatchContext(); // 2 + case DebugEvaluate: return v8InternalContext.IsDebugEvaluateContext(); // 3 + case Declaration: return v8InternalContext.is_declaration_context(); // 4 + case Eval: return v8InternalContext.IsEvalContext(); // 5 + case Function: return v8InternalContext.IsFunctionContext(); // 6 + case Module: return v8InternalContext.IsModuleContext(); // 7 + case Script: return v8InternalContext.IsScriptContext(); // 8 + case With: return v8InternalContext.IsWithContext(); // 9 + default:return false; + } + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_contextSetLength +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jint length) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + jboolean success = false; + if (IS_V8_CONTEXT(v8ValueType)) { + V8LocalContext v8ContextValue = v8LocalValue.As(); + V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); + v8InternalContext.set_length(length); + success = true; + } + return success; +} diff --git a/cpp/jni/com_caoccao_javet_interop_NodeNative.cpp b/cpp/jni/javet_jni_core_node.cpp similarity index 83% rename from cpp/jni/com_caoccao_javet_interop_NodeNative.cpp rename to cpp/jni/javet_jni_core_node.cpp index 2743b39cd..193d4f470 100644 --- a/cpp/jni/com_caoccao_javet_interop_NodeNative.cpp +++ b/cpp/jni/javet_jni_core_node.cpp @@ -15,17 +15,7 @@ * limitations under the License. */ -#include "com_caoccao_javet_interop_NodeNative.h" -#include "javet_callbacks.h" -#include "javet_converter.h" -#include "javet_enums.h" -#include "javet_exceptions.h" -#include "javet_inspector.h" -#include "javet_logging.h" -#include "javet_native.h" -#include "javet_node.h" -#include "javet_v8.h" -#include "javet_v8_runtime.h" +#include "javet_jni.h" JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_NodeNative_await (JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jint mAwaitMode) { @@ -51,4 +41,3 @@ JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_NodeNative_setPurgeEventLo v8Runtime->purgeEventLoopBeforeClose = purgeEventLoopBeforeClose; #endif } - diff --git a/cpp/jni/javet_jni_core_v8.cpp b/cpp/jni/javet_jni_core_v8.cpp new file mode 100644 index 000000000..130f18f04 --- /dev/null +++ b/cpp/jni/javet_jni_core_v8.cpp @@ -0,0 +1,449 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + + /* + * Development Guide: + * 1. Omitting namespace is not recommended in this project. + * 2. Methods are expected to be sorted alphabatically except JNI_OnLoad. + */ + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_allowCodeGenerationFromStrings +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jboolean allow) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + v8Context->AllowCodeGenerationFromStrings(allow); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_await +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jint mAwaitMode) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto umAwaitMode = static_cast(mAwaitMode); + return (jboolean)v8Runtime->Await(umAwaitMode); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_clearInternalStatistic +(JNIEnv* jniEnv, jobject caller) { +#ifdef ENABLE_MONITOR + GlobalJavetNativeMonitor.Clear(); +#endif +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_clearWeak +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_DATA_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (!v8PersistentDataPointer->IsEmpty() && v8PersistentDataPointer->IsWeak()) { + auto v8ValueReference = v8PersistentDataPointer->ClearWeak(); + v8ValueReference->Clear(); + delete v8ValueReference; + INCREASE_COUNTER(Javet::Monitor::CounterType::DeleteWeakCallbackReference); + } +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_cloneV8Value +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jboolean mReferenceCopy) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + V8LocalValue clonedV8LocalValue; + if (!mReferenceCopy + && !v8LocalValue->IsFunction() + && !v8LocalValue->IsMap() + && !v8LocalValue->IsSet() + && !v8LocalValue->IsWeakMap() + && !v8LocalValue->IsWeakSet() + && v8LocalValue->IsObject()) { + /* + * Not all objects can be value copied. + * V8 performs the CHECK(is_clonable_js_type || is_clonable_wasm_type). + * The object actually is shadow copied. + */ + clonedV8LocalValue = v8LocalValue.As()->Clone(); + } + else { + // Reference copy + clonedV8LocalValue = V8LocalValue::New(v8Context->GetIsolate(), v8LocalValue); + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, clonedV8LocalValue); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_closeV8Runtime +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + v8Runtime->ClearExternalException(jniEnv); + v8Runtime->ClearExternalV8Runtime(jniEnv); + delete v8Runtime; + INCREASE_COUNTER(Javet::Monitor::CounterType::DeleteV8Runtime); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_createV8Inspector +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mV8Inspector) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + v8Runtime->v8Inspector.reset(new Javet::Inspector::JavetInspector(v8Runtime, mV8Inspector)); +} + +/* +Creating multiple isolates allows running JavaScript code in multiple threads, truly parallel. +*/ +JNIEXPORT jlong JNICALL Java_com_caoccao_javet_interop_V8Native_createV8Runtime +(JNIEnv* jniEnv, jobject caller, jobject mRuntimeOptions) { +#ifdef ENABLE_NODE + auto v8Runtime = new Javet::V8Runtime(Javet::V8Native::GlobalV8Platform.get(), Javet::NodeNative::GlobalNodeArrayBufferAllocator); +#else + auto v8Runtime = new Javet::V8Runtime(Javet::V8Native::GlobalV8Platform.get()); +#endif + INCREASE_COUNTER(Javet::Monitor::CounterType::NewV8Runtime); + v8Runtime->CreateV8Isolate(); + v8Runtime->CreateV8Context(jniEnv, mRuntimeOptions); + return TO_JAVA_LONG(v8Runtime); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_equals +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle1, jlong v8ValueHandle2) { + RUNTIME_AND_2_VALUES_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle1, v8ValueHandle2); + V8MaybeBool v8MaybeBool = v8LocalValue1->Equals(v8Context, v8LocalValue2); + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + return false; + } + return v8MaybeBool.FromMaybe(false); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getGlobalObject +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + return Javet::Converter::ToExternalV8ValueGlobalObject(jniEnv, v8Runtime); +} + +JNIEXPORT jlongArray JNICALL Java_com_caoccao_javet_interop_V8Native_getInternalStatistic +(JNIEnv* jniEnv, jobject caller) { +#ifdef ENABLE_MONITOR + return GlobalJavetNativeMonitor.GetCounters(jniEnv); +#else + return nullptr; +#endif +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8HeapSpaceStatistics +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jint allocationSpace) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + return Javet::Monitor::GetHeapSpaceStatistics(jniEnv, v8Runtime->v8Isolate, allocationSpace); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8HeapStatistics +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + return Javet::Monitor::GetHeapStatistics(jniEnv, v8Runtime->v8Isolate); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_getV8SharedMemoryStatistics +(JNIEnv* jniEnv, jobject caller) { + return Javet::Monitor::GetV8SharedMemoryStatistics(jniEnv); +} + +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_getVersion +(JNIEnv* jniEnv, jobject caller) { + return Javet::Converter::ToJavaString(jniEnv, v8::V8::GetVersion()); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasInternalType +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueInternalType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + using namespace Javet::Enums::V8ValueInternalType; + switch (v8ValueInternalType) + { + case V8ValueInternalType::Undefined: return v8LocalValue->IsUndefined(); // 0 + case V8ValueInternalType::Null: return v8LocalValue->IsNull(); // 1 + case V8ValueInternalType::NullOrUndefined: return v8LocalValue->IsNullOrUndefined(); // 2 + case V8ValueInternalType::True: return v8LocalValue->IsTrue(); // 3 + case V8ValueInternalType::False: return v8LocalValue->IsFalse(); // 4 + case V8ValueInternalType::Name: return v8LocalValue->IsName(); // 5 + case V8ValueInternalType::String: return v8LocalValue->IsString(); // 6 + case V8ValueInternalType::Symbol: return v8LocalValue->IsSymbol(); // 7 + case V8ValueInternalType::Function: return v8LocalValue->IsFunction(); // 8 + case V8ValueInternalType::Array: return v8LocalValue->IsArray(); // 9 + case V8ValueInternalType::Object: return v8LocalValue->IsObject(); // 10 + case V8ValueInternalType::BigInt: return v8LocalValue->IsBigInt(); // 11 + case V8ValueInternalType::Boolean: return v8LocalValue->IsBoolean(); // 12 + case V8ValueInternalType::Number: return v8LocalValue->IsNumber(); // 13 + case V8ValueInternalType::External: return v8LocalValue->IsExternal(); // 14 + case V8ValueInternalType::Int32: return v8LocalValue->IsInt32(); // 15 + case V8ValueInternalType::Date: return v8LocalValue->IsDate(); // 16 + case V8ValueInternalType::ArgumentsObject: return v8LocalValue->IsArgumentsObject(); // 17 + case V8ValueInternalType::BigIntObject: return v8LocalValue->IsBigIntObject(); // 18 + case V8ValueInternalType::BooleanObject: return v8LocalValue->IsBooleanObject(); // 19 + case V8ValueInternalType::NumberObject: return v8LocalValue->IsNumberObject(); // 20 + case V8ValueInternalType::StringObject: return v8LocalValue->IsStringObject(); // 21 + case V8ValueInternalType::SymbolObject: return v8LocalValue->IsSymbolObject(); // 22 + case V8ValueInternalType::NativeError: return v8LocalValue->IsNativeError(); // 23 + case V8ValueInternalType::RegExp: return v8LocalValue->IsRegExp(); // 24 + case V8ValueInternalType::AsyncFunction: return v8LocalValue->IsAsyncFunction(); // 25 + case V8ValueInternalType::GeneratorFunction: return v8LocalValue->IsGeneratorFunction(); // 26 + case V8ValueInternalType::GeneratorObject: return v8LocalValue->IsGeneratorObject(); // 27 + case V8ValueInternalType::Promise: return v8LocalValue->IsPromise(); // 28 + case V8ValueInternalType::Map: return v8LocalValue->IsMap(); // 29 + case V8ValueInternalType::Set: return v8LocalValue->IsSet(); // 30 + case V8ValueInternalType::MapIterator: return v8LocalValue->IsMapIterator(); // 31 + case V8ValueInternalType::SetIterator: return v8LocalValue->IsSetIterator(); // 32 + case V8ValueInternalType::WeakMap: return v8LocalValue->IsWeakMap(); // 33 + case V8ValueInternalType::WeakSet: return v8LocalValue->IsWeakSet(); // 34 + case V8ValueInternalType::ArrayBuffer: return v8LocalValue->IsArrayBuffer(); // 35 + case V8ValueInternalType::ArrayBufferView: return v8LocalValue->IsArrayBufferView(); // 36 + case V8ValueInternalType::TypedArray: return v8LocalValue->IsTypedArray(); // 37 + case V8ValueInternalType::Uint8Array: return v8LocalValue->IsUint8Array(); // 38 + case V8ValueInternalType::Uint8ClampedArray: return v8LocalValue->IsUint8ClampedArray(); // 39 + case V8ValueInternalType::Int8Array: return v8LocalValue->IsInt8Array(); // 40 + case V8ValueInternalType::Uint16Array: return v8LocalValue->IsUint16Array(); // 41 + case V8ValueInternalType::Int16Array: return v8LocalValue->IsInt16Array(); // 42 + case V8ValueInternalType::Uint32Array: return v8LocalValue->IsUint32Array(); // 43 + case V8ValueInternalType::Int32Array: return v8LocalValue->IsInt32Array(); // 44 + case V8ValueInternalType::Float32Array: return v8LocalValue->IsFloat32Array(); // 45 + case V8ValueInternalType::Float64Array: return v8LocalValue->IsFloat64Array(); // 46 + case V8ValueInternalType::BigInt64Array: return v8LocalValue->IsBigInt64Array(); // 47 + case V8ValueInternalType::BigUint64Array: return v8LocalValue->IsBigUint64Array(); // 48 + case V8ValueInternalType::DataView: return v8LocalValue->IsDataView(); // 49 + case V8ValueInternalType::SharedArrayBuffer: return v8LocalValue->IsSharedArrayBuffer(); // 50 + case V8ValueInternalType::Proxy: return v8LocalValue->IsProxy(); // 51 + case V8ValueInternalType::WasmModuleObject: return v8LocalValue->IsWasmModuleObject(); // 52 + case V8ValueInternalType::ModuleNamespaceObject: return v8LocalValue->IsModuleNamespaceObject(); // 53 + default: + break; + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPendingException +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + return v8InternalIsolate->has_pending_exception(); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasPendingMessage +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + return v8InternalIsolate->has_pending_message(); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_hasScheduledException +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + return v8InternalIsolate->has_scheduled_exception(); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_idleNotificationDeadline +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong deadlineInMillis) { + if (deadlineInMillis > 0) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + v8Context->GetIsolate()->IdleNotificationDeadline(((long)deadlineInMillis) / 1000.0); + } +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isDead +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + return v8Runtime->v8Isolate->IsDead(); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isInUse +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + return v8Runtime->v8Isolate->IsInUse(); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_isWeak +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_DATA_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (!v8PersistentDataPointer->IsEmpty()) { + return (jboolean)v8PersistentDataPointer->IsWeak(); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_lockV8Runtime +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + if (v8Runtime->IsLocked()) { + return false; + } + v8Runtime->Lock(); + return true; +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_lowMemoryNotification +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + v8Context->GetIsolate()->LowMemoryNotification(); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_promoteScheduledException +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + if (v8InternalIsolate->has_scheduled_exception()) { + v8InternalIsolate->PromoteScheduledException(); + return true; + } + return false; +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_registerGCEpilogueCallback +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + v8Runtime->v8Isolate->AddGCEpilogueCallback(Javet::Callback::JavetGCEpilogueCallback); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_registerGCPrologueCallback +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + v8Runtime->v8Isolate->AddGCPrologueCallback(Javet::Callback::JavetGCPrologueCallback); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_registerV8Runtime +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mV8Runtime) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + v8Runtime->ClearExternalException(jniEnv); + v8Runtime->ClearExternalV8Runtime(jniEnv); + v8Runtime->externalV8Runtime = jniEnv->NewGlobalRef(mV8Runtime); + INCREASE_COUNTER(Javet::Monitor::CounterType::NewGlobalRef); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_removeJNIGlobalRef +(JNIEnv* jniEnv, jobject caller, jlong handle) { + jniEnv->DeleteGlobalRef((jobject)handle); + INCREASE_COUNTER(Javet::Monitor::CounterType::DeleteGlobalRef); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_removeReferenceHandle +(JNIEnv* jniEnv, jobject caller, jlong referenceHandle, jint referenceType) { + auto v8PersistentDataPointer = TO_V8_PERSISTENT_DATA_POINTER(referenceHandle); + v8PersistentDataPointer->Reset(); + delete v8PersistentDataPointer; + INCREASE_COUNTER(Javet::Monitor::CounterType::DeletePersistentReference); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_reportPendingMessages +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + return Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_requestGarbageCollectionForTesting +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jboolean fullGC) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + v8Context->GetIsolate()->RequestGarbageCollectionForTesting(fullGC + ? v8::Isolate::GarbageCollectionType::kFullGarbageCollection + : v8::Isolate::GarbageCollectionType::kMinorGarbageCollection); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_resetV8Context +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mRuntimeOptions) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + v8Runtime->CloseV8Context(); + v8Runtime->CreateV8Context(jniEnv, mRuntimeOptions); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_resetV8Isolate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mRuntimeOptions) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + v8Runtime->CloseV8Context(); + v8Runtime->CloseV8Isolate(); + v8Runtime->CreateV8Isolate(); + v8Runtime->CreateV8Context(jniEnv, mRuntimeOptions); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_sameValue +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle1, jlong v8ValueHandle2) { + RUNTIME_AND_2_VALUES_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle1, v8ValueHandle2); + return v8LocalValue1->SameValue(v8LocalValue2); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_setWeak +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject objectReference) { + RUNTIME_AND_DATA_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (!v8PersistentDataPointer->IsEmpty() && !v8PersistentDataPointer->IsWeak()) { + auto v8ValueReference = new Javet::Callback::V8ValueReference(jniEnv, objectReference); + INCREASE_COUNTER(Javet::Monitor::CounterType::NewWeakCallbackReference); + v8ValueReference->v8PersistentDataPointer = v8PersistentDataPointer; + v8PersistentDataPointer->SetWeak(v8ValueReference, Javet::Callback::JavetCloseWeakDataReference, v8::WeakCallbackType::kParameter); + } +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_strictEquals +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle1, jlong v8ValueHandle2) { + RUNTIME_AND_2_VALUES_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle1, v8ValueHandle2); + return v8LocalValue1->StrictEquals(v8LocalValue2); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_terminateExecution +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + v8Runtime->v8Isolate->TerminateExecution(); +} + +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_toString +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (!IS_V8_MODULE(v8ValueType) && !IS_V8_SCRIPT(v8ValueType)) { + V8MaybeLocalString v8MaybeLocalString = v8LocalValue->ToString(v8Context); + if (v8MaybeLocalString.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + return Javet::Converter::ToJavaString(jniEnv, v8Context, v8MaybeLocalString.ToLocalChecked()); + } + } + V8LocalString v8LocalString; + return Javet::Converter::ToJavaString(jniEnv, v8Context, v8LocalString); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_unlockV8Runtime +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + if (!v8Runtime->IsLocked()) { + return false; + } + v8Runtime->Unlock(); + return true; +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_unregisterGCEpilogueCallback +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + v8Runtime->v8Isolate->RemoveGCEpilogueCallback(Javet::Callback::JavetGCEpilogueCallback); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_unregisterGCPrologueCallback +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + auto v8Runtime = Javet::V8Runtime::FromHandle(v8RuntimeHandle); + v8Runtime->v8Isolate->RemoveGCPrologueCallback(Javet::Callback::JavetGCPrologueCallback); +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_v8InspectorSend +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mMessage) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + char const* umMessage = jniEnv->GetStringUTFChars(mMessage, nullptr); + std::string message(umMessage, jniEnv->GetStringUTFLength(mMessage)); + v8Runtime->v8Inspector->send(message); + jniEnv->ReleaseStringUTFChars(mMessage, umMessage); +} diff --git a/cpp/jni/javet_jni_function.cpp b/cpp/jni/javet_jni_function.cpp new file mode 100644 index 000000000..076b35f5a --- /dev/null +++ b/cpp/jni/javet_jni_function.cpp @@ -0,0 +1,624 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionCall +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject mReceiver, jboolean mResultRequired, jobjectArray mValues) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsFunction()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + V8MaybeLocalValue v8MaybeLocalValueResult; + auto umReceiver = Javet::Converter::ToV8Value(jniEnv, v8Context, mReceiver); + uint32_t valueCount = mValues == nullptr ? 0 : jniEnv->GetArrayLength(mValues); + if (valueCount > 0) { + auto umValuesPointer = Javet::Converter::ToV8Values(jniEnv, v8Context, mValues); + v8MaybeLocalValueResult = v8LocalValue.As()->Call(v8Context, umReceiver, valueCount, umValuesPointer.get()); + } + else { + v8MaybeLocalValueResult = v8LocalValue.As()->Call(v8Context, umReceiver, 0, nullptr); + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + else if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionCallAsConstructor +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobjectArray mValues) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsFunction()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + V8MaybeLocalValue v8MaybeLocalValueResult; + uint32_t valueCount = mValues == nullptr ? 0 : jniEnv->GetArrayLength(mValues); + if (valueCount > 0) { + auto umValuesPointer = Javet::Converter::ToV8Values(jniEnv, v8Context, mValues); + v8MaybeLocalValueResult = v8LocalValue.As()->CallAsConstructor(v8Context, valueCount, umValuesPointer.get()); + } + else { + v8MaybeLocalValueResult = v8LocalValue.As()->CallAsConstructor(v8Context, 0, nullptr); + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + else if (!v8MaybeLocalValueResult.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionCanDiscardCompiled +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { + return v8InternalShared.CanDiscardCompiled(); + } + } + return false; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionCompile +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mScript, jbyteArray mCachedData, + jstring mResourceName, jint mResourceLineOffset, jint mResourceColumnOffset, jint mScriptId, jboolean mIsWASM, + jobjectArray mArguments, jobjectArray mContextExtensions) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto umScript = Javet::Converter::ToV8String(jniEnv, v8Context, mScript); + jboolean isModule = false; + auto scriptOriginPointer = Javet::Converter::ToV8ScriptOringinPointer( + jniEnv, v8Context, mResourceName, mResourceLineOffset, mResourceColumnOffset, mScriptId, mIsWASM, isModule); + size_t argumentCount = 0; + size_t contextExtensionCount = 0; + std::unique_ptr argumentsPointer; + std::unique_ptr contextExtensionsPointer; + if (mArguments != nullptr) { + argumentCount = jniEnv->GetArrayLength(mArguments); + if (argumentCount > 0) { + argumentsPointer = Javet::Converter::ToV8Strings(jniEnv, v8Context, mArguments); + } + } + if (mContextExtensions != nullptr) { + contextExtensionCount = jniEnv->GetArrayLength(mContextExtensions); + if (contextExtensionCount > 0) { + contextExtensionsPointer = Javet::Converter::ToV8Objects(jniEnv, v8Context, mContextExtensions); + } + } + v8::MaybeLocal v8MaybeLocalFunction; + if (mCachedData) { + V8ScriptCompilerSource scriptSource( + umScript, *scriptOriginPointer.get(), Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); + v8MaybeLocalFunction = v8::ScriptCompiler::CompileFunction( + v8Context, &scriptSource, + argumentCount, argumentsPointer.get(), + contextExtensionCount, contextExtensionsPointer.get(), + v8::ScriptCompiler::kConsumeCodeCache); + LOG_DEBUG("Function cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); + } + else { + V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); + v8MaybeLocalFunction = v8::ScriptCompiler::CompileFunction( + v8Context, &scriptSource, + argumentCount, argumentsPointer.get(), + contextExtensionCount, contextExtensionsPointer.get()); + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + else if (!v8MaybeLocalFunction.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalFunction.ToLocalChecked()); + } + return nullptr; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionCopyScopeInfoFrom +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, + jlong targetV8ValueHandle, jint targetV8ValueType, + jlong sourceV8ValueHandle, jint sourceV8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, targetV8ValueHandle); + jboolean success = false; + if (IS_V8_FUNCTION(targetV8ValueType) && IS_V8_FUNCTION(sourceV8ValueType)) { + auto sourceV8PersistentValuePointer = TO_V8_PERSISTENT_VALUE_POINTER(sourceV8ValueHandle); + auto sourceV8LocalValue = sourceV8PersistentValuePointer->Get(v8Context->GetIsolate()); + auto targetV8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto sourceV8InternalFunction = Javet::Converter::ToV8InternalJSFunction(sourceV8LocalValue); + auto targetV8InternalShared = targetV8InternalFunction.shared(); + auto sourceV8InternalShared = sourceV8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(sourceV8InternalShared) && IS_USER_DEFINED_FUNCTION(targetV8InternalShared)) { + V8InternalDisallowGarbageCollection disallowGarbageCollection; + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + // Clone the shared function info + targetV8InternalShared = *v8InternalIsolate->factory()->CloneSharedFunctionInfo( + v8::internal::Handle(sourceV8InternalShared, v8InternalIsolate)); + // Clone the scope info + auto sourceScopeInfo = sourceV8InternalShared.scope_info(); + auto emptyBlocklistHandle = V8InternalStringSet::New(v8InternalIsolate); + auto targetScopeInfo = *V8InternalScopeInfo::RecreateWithBlockList( + v8InternalIsolate, v8::internal::Handle(sourceScopeInfo, v8InternalIsolate), emptyBlocklistHandle); + targetV8InternalShared.set_raw_scope_info(targetScopeInfo); + targetV8InternalFunction.set_shared(targetV8InternalShared, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); + success = true; + } + } + return success; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionCreate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mCallbackContext) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto javetCallbackContextReferencePointer = + new Javet::Callback::JavetCallbackContextReference(jniEnv, mCallbackContext); + INCREASE_COUNTER(Javet::Monitor::CounterType::NewJavetCallbackContextReference); + auto v8LocalContextHandle = + v8::BigInt::New(v8Context->GetIsolate(), TO_NATIVE_INT_64(javetCallbackContextReferencePointer)); + javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer = + new V8PersistentBigInt(v8Context->GetIsolate(), v8LocalContextHandle); + INCREASE_COUNTER(Javet::Monitor::CounterType::NewPersistentCallbackContextReference); + auto v8MaybeLocalFunction = + v8::Function::New(v8Context, Javet::Callback::JavetFunctionCallback, v8LocalContextHandle); + if (v8MaybeLocalFunction.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context, "Function allocation failed")) { + return nullptr; + } + } + else { + auto v8LocalFunction = v8MaybeLocalFunction.ToLocalChecked(); + if (!v8LocalFunction.IsEmpty()) { + javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer->SetWeak( + javetCallbackContextReferencePointer, + Javet::Callback::JavetCloseWeakCallbackContextHandle, + v8::WeakCallbackType::kParameter); + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalFunction); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionDiscardCompiled +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { + if (v8InternalShared.CanDiscardCompiled()) { + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + V8InternalSharedFunctionInfo::DiscardCompiled(v8InternalIsolate, v8::internal::Handle(v8InternalShared, v8InternalIsolate)); + return true; + } + } + } + return false; +} + +JNIEXPORT jobjectArray JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetArguments +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared) && v8InternalShared.is_wrapped()) { + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); + auto wrappedArguments = v8InternalScript.wrapped_arguments(); + auto length = wrappedArguments.length(); + if (length > 0) { + jobjectArray arguments = jniEnv->NewObjectArray(length, Javet::Converter::jclassString, nullptr); + for (int i = 0; i < length; ++i) { + auto v8InternalObjectHandle = v8::internal::Handle(wrappedArguments.get(i), v8InternalIsolate); + auto v8LocalString = v8::Utils::ToLocal(v8InternalObjectHandle).As(); + jstring argument = Javet::Converter::ToJavaString(jniEnv, v8Context, v8LocalString); + jniEnv->SetObjectArrayElement(arguments, i, argument); + } + return arguments; + } + } + } + return nullptr; +} + +JNIEXPORT jbyteArray JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetCachedData +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + if (IS_V8_FUNCTION(v8ValueType)) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { + auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); + if (v8InternalScript.is_wrapped()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + std::unique_ptr cachedDataPointer; + cachedDataPointer.reset(v8::ScriptCompiler::CreateCodeCacheForFunction(v8LocalValue.As())); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return nullptr; + } + if (cachedDataPointer) { + return Javet::Converter::ToJavaByteArray(jniEnv, cachedDataPointer.get()); + } + } + } + } + return nullptr; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetContext +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + if (v8InternalFunction.has_context()) { + auto v8InternalContextHandle = v8::internal::Handle(v8InternalFunction.context(), v8InternalIsolate); + auto v8LocalContext = v8::Utils::ToLocal(v8InternalContextHandle); + return Javet::Converter::ToExternalV8Context(jniEnv, v8Runtime, v8Context, v8LocalContext); + } + } + return nullptr; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetInternalProperties +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + // This feature is not enabled yet. + v8_inspector::V8InspectorClient v8InspectorClient; + v8_inspector::V8InspectorImpl v8InspectorImpl(v8Context->GetIsolate(), &v8InspectorClient); + v8_inspector::V8Debugger v8Debugger(v8Context->GetIsolate(), &v8InspectorImpl); + auto v8MaybeLocalArray = v8Debugger.internalProperties(v8Context, v8LocalValue.As()); + if (v8MaybeLocalArray.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalArray.ToLocalChecked()); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetJSFunctionType +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + using namespace Javet::Enums::JSFunctionType; + if (IS_V8_FUNCTION(v8ValueType)) { + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (v8InternalShared.native()) { + return JSFunctionType::Native; + } + else if (v8InternalShared.IsApiFunction()) { + return JSFunctionType::API; + } + else if (v8InternalShared.IsUserJavaScript()) { + return JSFunctionType::UserDefined; + } + } + return JSFunctionType::Unknown; +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetJSScopeType +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + auto v8InternalScopeInfo = v8InternalShared.scope_info(); + return v8InternalScopeInfo.scope_type(); + } + return Javet::Enums::JSScopeType::Unknown; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetScopeInfos +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, + jboolean includeGlobalVariables, jboolean includeScopeTypeGlobal) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + V8LocalArray v8LocalArray = v8::Array::New(v8Context->GetIsolate()); + if (IS_V8_FUNCTION(v8ValueType)) { + V8InternalDisallowGarbageCollection disallowGarbageCollection; + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + auto v8InternalScopeInfo = v8InternalShared.scope_info(); + V8InternalScopeIterator scopeIterator(v8InternalIsolate, v8::internal::Handle(v8InternalFunction, v8InternalIsolate)); + uint32_t index = 0; + for (; !scopeIterator.Done(); scopeIterator.Next()) { + auto type = scopeIterator.Type(); + if (!includeScopeTypeGlobal && type == V8InternalScopeIterator::ScopeTypeGlobal) { + continue; + } + V8LocalArray innerV8LocalArray = v8::Array::New(v8Context->GetIsolate(), INDEX_SCOPE_SIZE); + auto mode = includeGlobalVariables ? V8InternalScopeIterator::Mode::ALL : V8InternalScopeIterator::Mode::STACK; + auto scopeObject = scopeIterator.ScopeObject(mode); + auto v8LocalScopeObject = v8::Utils::ToLocal(scopeObject); + innerV8LocalArray->Set(v8Context, INDEX_SCOPE_TYPE, Javet::Converter::ToV8Integer(v8Context, (int)type)).ToChecked(); + innerV8LocalArray->Set(v8Context, INDEX_SCOPE_OBJECT, v8LocalScopeObject).ToChecked(); + innerV8LocalArray->Set(v8Context, INDEX_SCOPE_HAS_CONTEXT, Javet::Converter::ToV8Boolean(v8Context, scopeIterator.HasContext())).ToChecked(); + innerV8LocalArray->Set(v8Context, INDEX_SCOPE_START_POSITION, Javet::Converter::ToV8Integer(v8Context, scopeIterator.start_position())).ToChecked(); + innerV8LocalArray->Set(v8Context, INDEX_SCOPE_END_POSITION, Javet::Converter::ToV8Integer(v8Context, scopeIterator.end_position())).ToChecked(); + v8LocalArray->Set(v8Context, index, innerV8LocalArray).ToChecked(); + ++index; + } + } + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalArray); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetScriptSource +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + V8InternalDisallowGarbageCollection disallowGarbageCollection; + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { + auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); + auto v8InternalSource = V8InternalString::cast(v8InternalScript.source()); + const int startPosition = v8InternalShared.StartPosition(); + const int endPosition = v8InternalShared.EndPosition(); + const int sourceLength = v8InternalSource.length(); + auto sourceCode = v8InternalSource.ToCString( + V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL, + 0, sourceLength); + return jniEnv->NewObject( + Javet::Converter::jclassIV8ValueFunctionScriptSource, + Javet::Converter::jmethodIDIV8ValueFunctionScriptSourceConstructor, + Javet::Converter::ToJavaString(jniEnv, sourceCode.get()), + startPosition, + endPosition); + } + } + return nullptr; +} + +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_functionGetSourceCode +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { + auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); + auto v8InternalSource = V8InternalString::cast(v8InternalScript.source()); + const int startPosition = v8InternalShared.StartPosition(); + const int endPosition = v8InternalShared.EndPosition(); + auto sourceCode = v8InternalSource.ToCString( + V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL, + startPosition, endPosition - startPosition); + return Javet::Converter::ToJavaString(jniEnv, sourceCode.get()); + } + } + return nullptr; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionIsCompiled +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { + return v8InternalShared.is_compiled(); + } + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionIsWrapped +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_FUNCTION(v8ValueType)) { + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { + return v8InternalShared.is_wrapped(); + } + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetContext +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject mV8ContextValue) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + jboolean success = false; + if (IS_V8_FUNCTION(v8ValueType)) { + V8InternalDisallowGarbageCollection disallowGarbageCollection; + V8LocalContext v8ContextValue = Javet::Converter::ToV8Context(jniEnv, v8Context, mV8ContextValue); + V8InternalContext v8InternalContext = Javet::Converter::ToV8InternalContext(v8ContextValue); + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + v8InternalFunction.set_context(v8InternalContext); + success = true; + } + return success; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetScriptSource +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject mScriptSource, jboolean mCloneScript) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + jboolean success = false; + if (IS_V8_FUNCTION(v8ValueType)) { + V8InternalDisallowGarbageCollection disallowGarbageCollection; + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { + auto v8InternalScopeInfo = v8InternalShared.scope_info(); + if (v8InternalScopeInfo.scope_type() == V8InternalScopeType::FUNCTION_SCOPE) { + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + auto mSourceCode = (jstring)jniEnv->CallObjectMethod(mScriptSource, Javet::Converter::jmethodIDIV8ValueFunctionScriptGetCode); + auto umSourceCode = Javet::Converter::ToV8String(jniEnv, v8Context, mSourceCode); + const int startPosition = jniEnv->CallIntMethod(mScriptSource, Javet::Converter::jmethodIDIV8ValueFunctionScriptGetStartPosition); + const int endPosition = jniEnv->CallIntMethod(mScriptSource, Javet::Converter::jmethodIDIV8ValueFunctionScriptGetEndPosition); + auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); + auto v8InternalSource = v8::Utils::OpenHandle(*umSourceCode); + bool sourceCodeEquals = v8InternalScript.source().StrictEquals(*v8InternalSource); + bool positionEquals = startPosition == v8InternalShared.StartPosition() && endPosition == v8InternalShared.EndPosition(); + if (!sourceCodeEquals || !positionEquals) { + if (v8InternalShared.CanDiscardCompiled()) { + V8InternalSharedFunctionInfo::DiscardCompiled(v8InternalIsolate, v8::internal::Handle(v8InternalShared, v8InternalIsolate)); + v8InternalShared.set_allows_lazy_compilation(true); + } + if (!sourceCodeEquals) { + auto v8InternalScriptHandle = v8::internal::Handle(v8InternalScript, v8InternalIsolate); + if (mCloneScript) { +#ifdef ENABLE_NODE + auto clonedV8InternalScript = v8InternalIsolate->factory()->CloneScript(v8InternalScriptHandle); + clonedV8InternalScript->set_source(*v8InternalSource, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); +#else + auto clonedV8InternalScript = v8InternalIsolate->factory()->CloneScript(v8InternalScriptHandle, v8InternalSource); +#endif + v8InternalShared.set_script(*clonedV8InternalScript); + } + else { +#ifdef ENABLE_NODE + v8InternalScript.set_source(*v8InternalSource, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); +#else + V8InternalScript::SetSource(v8InternalIsolate, v8InternalScriptHandle, v8InternalSource); +#endif + } + } + if (!positionEquals) { + v8InternalScopeInfo.SetPositionInfo(startPosition, endPosition); + } + success = true; + } + DELETE_LOCAL_REF(jniEnv, mSourceCode); + } + } + } + return success; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_functionSetSourceCode +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mSourceCode, jboolean mCloneScript) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + jboolean success = false; + if (IS_V8_FUNCTION(v8ValueType)) { + V8InternalDisallowGarbageCollection disallowGarbageCollection; + auto v8InternalFunction = Javet::Converter::ToV8InternalJSFunction(v8LocalValue); + auto v8InternalShared = v8InternalFunction.shared(); + if (IS_USER_DEFINED_FUNCTION(v8InternalShared)) { + auto v8InternalScopeInfo = v8InternalShared.scope_info(); + while (v8InternalScopeInfo.scope_type() == V8InternalScopeType::FUNCTION_SCOPE) { + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + auto v8InternalScript = V8InternalScript::cast(v8InternalShared.script()); + auto v8InternalSource = V8InternalString::cast(v8InternalScript.source()); + const int startPosition = v8InternalShared.StartPosition(); + const int endPosition = v8InternalShared.EndPosition(); + const int sourceLength = v8InternalSource.length(); + + // Build the new source code. + auto umSourceCode = Javet::Converter::ToV8String(jniEnv, v8Context, mSourceCode); + + V8LocalString newSourceCode; + if (startPosition > 0) { + int utf8Length = 0; + auto stdStringHeader(v8InternalSource.ToCString( + V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL, + 0, startPosition, &utf8Length)); + auto v8MaybeLocalStringHeader = v8::String::NewFromUtf8( + v8Context->GetIsolate(), stdStringHeader.get(), v8::NewStringType::kNormal, utf8Length); + if (v8MaybeLocalStringHeader.IsEmpty()) { + Javet::Exceptions::HandlePendingException( + jniEnv, v8Runtime, v8Context, "header could not be extracted from the source code"); + break; + } + newSourceCode = v8MaybeLocalStringHeader.ToLocalChecked(); + } + if (newSourceCode.IsEmpty()) { + newSourceCode = umSourceCode; + } + else { + newSourceCode = v8::String::Concat(v8Context->GetIsolate(), newSourceCode, umSourceCode); + } + if (endPosition < sourceLength) { + int utf8Length = 0; + auto stdStringFooter(v8InternalSource.ToCString( + V8InternalAllowNullsFlag::DISALLOW_NULLS, V8InternalRobustnessFlag::ROBUST_STRING_TRAVERSAL, + endPosition, sourceLength - endPosition, &utf8Length)); + auto v8MaybeLocalStringFooter = v8::String::NewFromUtf8( + v8Context->GetIsolate(), stdStringFooter.get(), v8::NewStringType::kNormal, utf8Length); + if (v8MaybeLocalStringFooter.IsEmpty()) { + Javet::Exceptions::HandlePendingException( + jniEnv, v8Runtime, v8Context, "footer could not be extracted from the source code"); + break; + } + auto v8LocalStringFooter = v8MaybeLocalStringFooter.ToLocalChecked(); + if (newSourceCode.IsEmpty()) { + newSourceCode = v8LocalStringFooter; + } + else { + newSourceCode = v8::String::Concat(v8Context->GetIsolate(), newSourceCode, v8LocalStringFooter); + } + } + + /* + * Set the source and update the start and end position. + * Note: The source code is shared among all script objects, but position info is not. + * So the caller is responsible for restoring the original source code, + * otherwise the next script execution will likely fail because the position info + * of the next script is incorrect. + */ + const int newSourceLength = umSourceCode->Length(); + const int newEndPosition = startPosition + newSourceLength; + + auto newV8InternalSource = v8::Utils::OpenHandle(*newSourceCode); + bool sourceCodeEquals = v8InternalSource.StrictEquals(*newV8InternalSource); + bool positionEquals = newEndPosition == v8InternalShared.EndPosition(); + + if (!sourceCodeEquals || !positionEquals) { + // Discard compiled data and set lazy compile. + if (v8InternalShared.CanDiscardCompiled()) { + V8InternalSharedFunctionInfo::DiscardCompiled(v8InternalIsolate, v8::internal::Handle(v8InternalShared, v8InternalIsolate)); + v8InternalShared.set_allows_lazy_compilation(true); + } + if (!sourceCodeEquals) { + auto v8InternalScriptHandle = v8::internal::Handle(v8InternalScript, v8InternalIsolate); + if (mCloneScript) { +#ifdef ENABLE_NODE + auto clonedV8InternalScript = v8InternalIsolate->factory()->CloneScript(v8InternalScriptHandle); + clonedV8InternalScript->set_source(*newV8InternalSource, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); +#else + auto clonedV8InternalScript = v8InternalIsolate->factory()->CloneScript(v8InternalScriptHandle, newV8InternalSource); +#endif + v8InternalShared.set_script(*clonedV8InternalScript); + } + else { +#ifdef ENABLE_NODE + v8InternalScript.set_source(*newV8InternalSource, V8InternalWriteBarrierMode::UPDATE_WRITE_BARRIER); +#else + V8InternalScript::SetSource(v8InternalIsolate, v8InternalScriptHandle, newV8InternalSource); +#endif + } + } + if (!positionEquals) { + v8InternalScopeInfo.SetPositionInfo(startPosition, newEndPosition); + } + success = true; + } + break; + } + } + } + return success; +} diff --git a/cpp/jni/javet_jni_map.cpp b/cpp/jni/javet_jni_map.cpp new file mode 100644 index 000000000..5b01cd751 --- /dev/null +++ b/cpp/jni/javet_jni_map.cpp @@ -0,0 +1,404 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +namespace Javet { + namespace V8ValueMap { + const jboolean defaultPrimitiveFlags[] = { JNI_FALSE }; + template + T mapGet( + JNIEnv* jniEnv, + V8Runtime* v8Runtime, + const V8LocalContext& v8Context, + V8LocalValue v8LocalValue, + jint v8ValueType, + jobject key, + jbooleanArray primitiveFlags, + T(convert)(JNIEnv* jniEnv, V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray primitiveFlags), + T(fallback)(JNIEnv* jniEnv, V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray primitiveFlags), + T(except)(JNIEnv* jniEnv, V8Runtime* v8Runtime, const V8LocalContext& v8Context)) { + if (IS_V8_MAP(v8ValueType)) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8LocalValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + if (v8LocalValueKey.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return except(jniEnv, v8Runtime, v8Context); + } + } + else { + V8MaybeLocalValue v8MaybeLocalValue = v8LocalValue.As()->Get(v8Context, v8LocalValueKey); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return except(jniEnv, v8Runtime, v8Context); + } + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return except(jniEnv, v8Runtime, v8Context); + } + } + else { + return convert(jniEnv, v8Runtime, v8Context, v8MaybeLocalValue.ToLocalChecked(), primitiveFlags); + } + } + } + return fallback(jniEnv, v8Runtime, v8Context, primitiveFlags); + } + + bool mapSet( + JNIEnv* jniEnv, + V8Runtime* v8Runtime, + const V8LocalContext& v8Context, + const V8LocalMap& v8LocalMap, + const jobject key, + const V8LocalValue& v8LocalValueValue) { + V8MaybeBool v8MaybeBool = v8::Just(false); + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8LocalValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (!v8LocalValueKey.IsEmpty()) { + auto v8MaybeLocalMap = v8LocalMap->Set(v8Context, v8LocalValueKey, v8LocalValueValue); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (v8MaybeLocalMap.IsEmpty()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + return false; + } + return true; + } + return false; + } + } +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_mapCreate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8LocalMap = v8::Map::New(v8Context->GetIsolate()); + if (!v8LocalMap.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalMap); + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapDelete +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + V8MaybeBool v8MaybeBool = v8LocalValue.As()->Delete(v8Context, v8ValueKey); + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + else { + return v8MaybeBool.FromMaybe(false); + } + } + return false; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_mapGet +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueMap::mapGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + nullptr, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jobject { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalValue); + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jobject { + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jobject { return nullptr; }); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetBoolean +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jbooleanArray mPrimitiveFlags) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueMap::mapGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + mPrimitiveFlags, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jboolean { + if (v8LocalValue->IsBoolean() || v8LocalValue->IsBooleanObject()) { + return v8LocalValue->IsTrue(); + } + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueMap::defaultPrimitiveFlags); + return false; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jboolean { + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueMap::defaultPrimitiveFlags); + return false; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jboolean { return false; }); +} + +JNIEXPORT jdouble JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetDouble +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jbooleanArray mPrimitiveFlags) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueMap::mapGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + mPrimitiveFlags, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jdouble { + if (v8LocalValue->IsNumber() || v8LocalValue->IsNumberObject()) { + return v8LocalValue->NumberValue(v8Context).FromMaybe(0); + } + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueMap::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jdouble { + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueMap::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jdouble { return 0; }); +} +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetInteger +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jbooleanArray mPrimitiveFlags) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueMap::mapGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + mPrimitiveFlags, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jint { + if (v8LocalValue->IsInt32()) { + return v8LocalValue->Int32Value(v8Context).FromMaybe(0); + } + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueMap::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jint { + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueMap::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jint { return 0; }); +} + +JNIEXPORT jlong JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetLong +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jbooleanArray mPrimitiveFlags) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueMap::mapGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + mPrimitiveFlags, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jlong { + if (v8LocalValue->IsBigInt() || v8LocalValue->IsBigIntObject()) { + return v8LocalValue->ToBigInt(v8Context).ToLocalChecked()->Int64Value(); + } + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueMap::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jlong { + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueMap::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jlong { return 0; }); +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetSize +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + return (jint)v8LocalValue.As()->Size(); + } + return 0; +} + +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_mapGetString +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueMap::mapGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + nullptr, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jstring { + if (v8LocalValue->IsString()) { + return Javet::Converter::ToJavaString(jniEnv, v8Context, v8LocalValue); + } + return nullptr; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jstring { return nullptr; }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jstring { return nullptr; }); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapHas +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8LocalValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, value); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (!v8LocalValueKey.IsEmpty()) { + V8MaybeBool v8MaybeBool = v8LocalValue.As()->Has(v8Context, v8LocalValueKey); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + return false; + } + return v8MaybeBool.FromMaybe(false); + } + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSet +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobjectArray keysAndValues) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + auto length = jniEnv->GetArrayLength(keysAndValues); + if (length == 0 || length % 2 != 0) { + return false; + } + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8LocalMap = v8LocalValue.As(); + for (int i = 0; i < length; i += 2) { + auto jobjectValue = jniEnv->GetObjectArrayElement(keysAndValues, i + 1); + auto v8LocalValueValue = Javet::Converter::ToV8Value(jniEnv, v8Context, jobjectValue); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + auto jobjectKey = jniEnv->GetObjectArrayElement(keysAndValues, i); + if (!Javet::V8ValueMap::mapSet( + jniEnv, + v8Runtime, + v8Context, + v8LocalMap, + jobjectKey, + v8LocalValueValue)) { + return false; + } + } + return true; + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetBoolean +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jboolean value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + auto v8LocalMap = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Boolean(v8Context, value); + return Javet::V8ValueMap::mapSet(jniEnv, v8Runtime, v8Context, v8LocalMap, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetDouble +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jdouble value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + auto v8LocalMap = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Double(v8Context, value); + return Javet::V8ValueMap::mapSet(jniEnv, v8Runtime, v8Context, v8LocalMap, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetInteger +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jint value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + auto v8LocalMap = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Integer(v8Context, value); + return Javet::V8ValueMap::mapSet(jniEnv, v8Runtime, v8Context, v8LocalMap, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetLong +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jlong value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + auto v8LocalMap = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Long(v8Context, value); + return Javet::V8ValueMap::mapSet(jniEnv, v8Runtime, v8Context, v8LocalMap, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetNull +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + auto v8LocalMap = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Null(v8Context); + return Javet::V8ValueMap::mapSet(jniEnv, v8Runtime, v8Context, v8LocalMap, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetString +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jstring value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + auto v8LocalMap = v8LocalValue.As(); + auto v8LocalValueValue = value == nullptr + ? Javet::Converter::ToV8Null(v8Context).As() + : Javet::Converter::ToV8String(jniEnv, v8Context, value).As(); + return Javet::V8ValueMap::mapSet(jniEnv, v8Runtime, v8Context, v8LocalMap, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_mapSetUndefined +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_MAP(v8ValueType)) { + auto v8LocalMap = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Undefined(v8Context); + return Javet::V8ValueMap::mapSet(jniEnv, v8Runtime, v8Context, v8LocalMap, key, v8LocalValueValue); + } + return false; +} diff --git a/cpp/jni/javet_jni_module.cpp b/cpp/jni/javet_jni_module.cpp new file mode 100644 index 000000000..0d68c90c0 --- /dev/null +++ b/cpp/jni/javet_jni_module.cpp @@ -0,0 +1,174 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleCompile +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mScript, jbyteArray mCachedData, jboolean mResultRequired, + jstring mResourceName, jint mResourceLineOffset, jint mResourceColumnOffset, jint mScriptId, jboolean mIsWASM, jboolean mIsModule) { + if (mIsModule) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto umScript = Javet::Converter::ToV8String(jniEnv, v8Context, mScript); + auto scriptOriginPointer = Javet::Converter::ToV8ScriptOringinPointer( + jniEnv, v8Context, mResourceName, mResourceLineOffset, mResourceColumnOffset, mScriptId, mIsWASM, mIsModule); + v8::MaybeLocal v8MaybeLocalCompiledModule; + if (mCachedData) { + V8ScriptCompilerSource scriptSource( + umScript, + *scriptOriginPointer.get(), + Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); + v8MaybeLocalCompiledModule = v8::ScriptCompiler::CompileModule( + v8Context->GetIsolate(), + &scriptSource, + v8::ScriptCompiler::kConsumeCodeCache); + LOG_DEBUG("Module cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); + } + else { + V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); + v8MaybeLocalCompiledModule = v8::ScriptCompiler::CompileModule(v8Context->GetIsolate(), &scriptSource); + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + else if (mResultRequired && !v8MaybeLocalCompiledModule.IsEmpty()) { + return Javet::Converter::ToExternalV8Module(jniEnv, v8Runtime, v8Context, v8MaybeLocalCompiledModule.ToLocalChecked()); + } + } + return nullptr; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleEvaluate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jboolean mResultRequired) { + RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalModule->GetStatus() == v8::Module::Status::kInstantiated) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8MaybeLocalValueResult = v8LocalModule->Evaluate(v8Context); + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { + Javet::Exceptions::ClearJNIException(jniEnv); + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); + } + } + Javet::Exceptions::ClearJNIException(jniEnv); + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleExecute +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mScript, jbyteArray mCachedData, jboolean mResultRequired, + jstring mResourceName, jint mResourceLineOffset, jint mResourceColumnOffset, jint mScriptId, jboolean mIsWASM) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto umScript = Javet::Converter::ToV8String(jniEnv, v8Context, mScript); + auto scriptOriginPointer = Javet::Converter::ToV8ScriptOringinPointer( + jniEnv, v8Context, mResourceName, mResourceLineOffset, mResourceColumnOffset, mScriptId, mIsWASM, true); + v8::MaybeLocal v8MaybeLocalCompiledModule; + if (mCachedData) { + V8ScriptCompilerSource scriptSource( + umScript, *scriptOriginPointer.get(), Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); + v8MaybeLocalCompiledModule = v8::ScriptCompiler::CompileModule( + v8Context->GetIsolate(), &scriptSource, v8::ScriptCompiler::kConsumeCodeCache); + LOG_DEBUG("Module cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); + } + else { + V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); + v8MaybeLocalCompiledModule = v8::ScriptCompiler::CompileModule(v8Context->GetIsolate(), &scriptSource); + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + else if (!v8MaybeLocalCompiledModule.IsEmpty()) { + auto compliedModule = v8MaybeLocalCompiledModule.ToLocalChecked(); + auto v8MaybeBool = compliedModule->InstantiateModule(v8Context, Javet::Callback::JavetModuleResolveCallback); + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + else if (v8MaybeBool.FromMaybe(false)) { + auto v8MaybeLocalValueResult = compliedModule->Evaluate(v8Context); + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { + Javet::Exceptions::ClearJNIException(jniEnv); + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); + } + } + } + Javet::Exceptions::ClearJNIException(jniEnv); + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jbyteArray JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetCachedData +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + if (IS_V8_MODULE(v8ValueType)) { + RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + std::unique_ptr cachedDataPointer; + cachedDataPointer.reset(v8::ScriptCompiler::CreateCodeCache(v8LocalModule->GetUnboundModuleScript())); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return nullptr; + } + if (cachedDataPointer) { + return Javet::Converter::ToJavaByteArray(jniEnv, cachedDataPointer.get()); + } + } + return nullptr; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetException +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalModule->GetStatus() == v8::Module::Status::kErrored) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalModule->GetException()); + } + return nullptr; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetNamespace +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalModule->GetModuleNamespace()); +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetScriptId +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return (jint)v8LocalModule->ScriptId(); +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_moduleGetStatus +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return (jint)v8LocalModule->GetStatus(); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_moduleInstantiate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_MODULE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalModule->GetStatus() == v8::Module::Status::kUninstantiated) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8MaybeBool = v8LocalModule->InstantiateModule(v8Context, Javet::Callback::JavetModuleResolveCallback); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} diff --git a/cpp/jni/javet_jni_object.cpp b/cpp/jni/javet_jni_object.cpp new file mode 100644 index 000000000..f970e752e --- /dev/null +++ b/cpp/jni/javet_jni_object.cpp @@ -0,0 +1,874 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +namespace Javet { + namespace V8ValueObject { + const jboolean defaultPrimitiveFlags[] = { JNI_FALSE }; + + template + T objectGet( + JNIEnv* jniEnv, + V8Runtime* v8Runtime, + const V8LocalContext& v8Context, + V8LocalValue v8LocalValue, + jint v8ValueType, + jobject key, + jbooleanArray primitiveFlags, + T(convert)(JNIEnv* jniEnv, V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray primitiveFlags), + T(fallback)(JNIEnv* jniEnv, V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray primitiveFlags), + T(except)(JNIEnv* jniEnv, V8Runtime* v8Runtime, const V8LocalContext& v8Context)) { + if (IS_V8_SYMBOL(v8ValueType)) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return except(jniEnv, v8Runtime, v8Context); + } + } + else { + v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); + } + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return except(jniEnv, v8Runtime, v8Context); + } + } + if (v8LocalValue->IsObject()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8LocalValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + if (v8LocalValueKey.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return except(jniEnv, v8Runtime, v8Context); + } + } + else { + auto v8LocalObject = v8LocalValue.As(); + V8MaybeLocalValue v8MaybeLocalValue; + if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { + jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); + v8MaybeLocalValue = v8LocalObject->Get(v8Context, integerKey); + } + else { + v8MaybeLocalValue = v8LocalObject->Get(v8Context, v8LocalValueKey); + } + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return except(jniEnv, v8Runtime, v8Context); + } + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return except(jniEnv, v8Runtime, v8Context); + } + } + else { + return convert(jniEnv, v8Runtime, v8Context, v8MaybeLocalValue.ToLocalChecked(), primitiveFlags); + } + } + } + return fallback(jniEnv, v8Runtime, v8Context, primitiveFlags); + } + + bool objectSet( + JNIEnv* jniEnv, + V8Runtime* v8Runtime, + const V8LocalContext& v8Context, + const V8LocalObject& v8LocalObject, + const jobject key, + const V8LocalValue& v8LocalValueValue) { + V8MaybeBool v8MaybeBool = v8::Just(false); + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { + jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); + v8MaybeBool = v8LocalObject->Set(v8Context, integerKey, v8LocalValueValue); + } + else { + auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (!v8ValueKey.IsEmpty()) { + v8MaybeBool = v8LocalObject->Set(v8Context, v8ValueKey, v8LocalValueValue); + } + } + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + return false; + } + return v8MaybeBool.FromMaybe(false); + } + } +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_batchObjectGet +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, + jobjectArray v8ValueKeys, jobjectArray v8ValueValues, jint length) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + int keyLength = jniEnv->GetArrayLength(v8ValueKeys); + length = length > keyLength ? keyLength : length; + if (length > 0) { + auto v8LocalObject = v8LocalValue.As(); + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + for (int i = 0; i < length; ++i) { + V8MaybeLocalValue v8MaybeLocalValueResult; + auto key = jniEnv->GetObjectArrayElement(v8ValueKeys, i); + if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { + jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); + v8MaybeLocalValueResult = v8LocalObject->Get(v8Context, integerKey); + } + else { + auto v8LocalValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + v8MaybeLocalValueResult = v8LocalObject->Get(v8Context, v8LocalValueKey); + } + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return i; + } + V8LocalValue v8LocalValueValue; + if (v8MaybeLocalValueResult.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return i; + } + } + else { + v8LocalValueValue = v8MaybeLocalValueResult.ToLocalChecked(); + } + jniEnv->SetObjectArrayElement( + v8ValueValues, + i, + Javet::Converter::ToExternalV8Value(jniEnv, v8Runtime, v8Context, v8LocalValueValue)); + } + } + return length; + } + return 0; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectCreate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8LocalObject = v8::Object::New(v8Context->GetIsolate()); + if (!v8LocalObject.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalObject); + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectDelete +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + V8MaybeBool v8MaybeBool = v8::Just(false); + auto v8LocalObject = v8LocalValue.As(); + if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { + jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); + v8MaybeBool = v8LocalObject->Delete(v8Context, integerKey); + } + else { + auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + v8MaybeBool = v8LocalObject->Delete(v8Context, v8ValueKey); + } + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + else { + return v8MaybeBool.FromMaybe(false); + } + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectDeletePrivateProperty +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mKey) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + auto v8LocalStringKey = Javet::Converter::ToV8String(jniEnv, v8Context, mKey); + auto v8LocalPrivateKey = v8::Private::ForApi(v8Context->GetIsolate(), v8LocalStringKey); + auto v8MaybeBool = v8LocalValue.As()->DeletePrivate(v8Context, v8LocalPrivateKey); + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGet +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueObject::objectGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + nullptr, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jobject { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalValue); + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jobject { + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jobject { return nullptr; }); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetBoolean +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jbooleanArray mPrimitiveFlags) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueObject::objectGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + mPrimitiveFlags, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jboolean { + if (v8LocalValue->IsBoolean() || v8LocalValue->IsBooleanObject()) { + return v8LocalValue->IsTrue(); + } + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueObject::defaultPrimitiveFlags); + return false; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jboolean { + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueObject::defaultPrimitiveFlags); + return false; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jboolean { return false; }); +} + +JNIEXPORT jdouble JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetDouble +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jbooleanArray mPrimitiveFlags) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueObject::objectGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + mPrimitiveFlags, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jdouble { + if (v8LocalValue->IsNumber() || v8LocalValue->IsNumberObject()) { + return v8LocalValue->NumberValue(v8Context).FromMaybe(0); + } + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueObject::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jdouble { + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueObject::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jdouble { return 0; }); +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetIdentityHash +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + return v8LocalValue.As()->GetIdentityHash(); + } + return 0; +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetInteger +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jbooleanArray mPrimitiveFlags) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueObject::objectGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + mPrimitiveFlags, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jint { + if (v8LocalValue->IsInt32()) { + return v8LocalValue->Int32Value(v8Context).FromMaybe(0); + } + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueObject::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jint { + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueObject::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jint { return 0; }); +} + +JNIEXPORT jlong JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetLong +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jbooleanArray mPrimitiveFlags) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueObject::objectGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + mPrimitiveFlags, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jlong { + if (v8LocalValue->IsBigInt() || v8LocalValue->IsBigIntObject()) { + return v8LocalValue->ToBigInt(v8Context).ToLocalChecked()->Int64Value(); + } + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueObject::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jlong { + jniEnv->SetBooleanArrayRegion(mPrimitiveFlags, 0, 1, Javet::V8ValueObject::defaultPrimitiveFlags); + return 0; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jlong { return 0; }); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetPrivateProperty +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mKey) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8LocalStringKey = Javet::Converter::ToV8String(jniEnv, v8Context, mKey); + auto v8LocalPrivateKey = v8::Private::ForApi(v8Context->GetIsolate(), v8LocalStringKey); + auto v8MaybeLocalValue = v8LocalValue.As()->GetPrivate(v8Context, v8LocalPrivateKey); + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValue.ToLocalChecked()); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetProperty +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_SYMBOL(v8ValueType)) { + auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); + } + } + if (v8LocalValue->IsObject()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8LocalObject = v8LocalValue.As(); + V8MaybeLocalValue v8MaybeLocalValueValue; + if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { + jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); + v8MaybeLocalValueValue = v8LocalObject->Get(v8Context, integerKey); + } + else { + auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + if (v8ValueKey.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + v8MaybeLocalValueValue = v8LocalObject->Get(v8Context, v8ValueKey); + } + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + if (v8MaybeLocalValueValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueValue.ToLocalChecked()); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetOwnPropertyNames +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_SYMBOL(v8ValueType)) { + auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); + } + } + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + auto v8MaybeLocalArray = v8LocalObject->GetOwnPropertyNames(v8Context); + if (v8MaybeLocalArray.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalArray.ToLocalChecked()); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetPropertyNames +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_SYMBOL(v8ValueType)) { + auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); + } + } + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + auto v8MaybeLocalArray = v8LocalObject->GetPropertyNames(v8Context); + if (v8MaybeLocalArray.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalArray.ToLocalChecked()); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetPrototype +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + V8LocalValue v8LocalValueResult = v8LocalObject->GetPrototype(); + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalValueResult); + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_objectGetString +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + return Javet::V8ValueObject::objectGet( + jniEnv, + v8Runtime, + v8Context, + v8LocalValue, + v8ValueType, + key, + nullptr, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, const V8LocalValue& v8LocalValue, jbooleanArray mPrimitiveFlags) -> jstring { + if (v8LocalValue->IsString()) { + return Javet::Converter::ToJavaString(jniEnv, v8Context, v8LocalValue); + } + return nullptr; + }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context, jbooleanArray mPrimitiveFlags) -> jstring { return nullptr; }, + [](JNIEnv* jniEnv, Javet::V8Runtime* v8Runtime, const V8LocalContext& v8Context) -> jstring { return nullptr; }); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectHas +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + V8MaybeBool v8MaybeBool = v8::Just(false); + auto v8LocalObject = v8LocalValue.As(); + if (Javet::Converter::IsV8ValueInteger(jniEnv, value)) { + jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, value); + v8MaybeBool = v8LocalObject->Has(v8Context, integerKey); + } + else { + auto v8LocalValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, value); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (!v8LocalValueKey.IsEmpty()) { + v8MaybeBool = v8LocalObject->Has(v8Context, v8LocalValueKey); + } + } + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + return false; + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectHasOwnProperty +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_SYMBOL(v8ValueType)) { + auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return false; + } + } + else { + v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); + } + } + if (v8LocalValue->IsObject()) { + V8MaybeBool v8MaybeBool = v8::Just(false); + auto v8LocalObject = v8LocalValue.As(); + if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { + jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); + v8MaybeBool = v8LocalObject->HasOwnProperty(v8Context, integerKey); + } + else if (Javet::Converter::IsV8ValueString(jniEnv, key)) { + jstring stringKey = Javet::Converter::ToJavaStringFromV8ValueString(jniEnv, key); + auto v8ValueKey = Javet::Converter::ToV8String(jniEnv, v8Context, stringKey); + v8MaybeBool = v8LocalObject->HasOwnProperty(v8Context, v8ValueKey); + } + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectHasPrivateProperty +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mKey) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + auto v8LocalStringKey = Javet::Converter::ToV8String(jniEnv, v8Context, mKey); + auto v8LocalPrivateKey = v8::Private::ForApi(v8Context->GetIsolate(), v8LocalStringKey); + auto v8MaybeBool = v8LocalValue.As()->HasPrivate(v8Context, v8LocalPrivateKey); + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_objectInvoke +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mFunctionName, jboolean mResultRequired, jobjectArray mValues) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_SYMBOL(v8ValueType)) { + auto v8MaybeLocalValue = v8LocalValue->ToObject(v8Context); + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + v8LocalValue = v8MaybeLocalValue.ToLocalChecked(); + } + } + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + auto v8MaybeLocalValue = v8LocalObject->Get(v8Context, Javet::Converter::ToV8String(jniEnv, v8Context, mFunctionName)); + if (v8MaybeLocalValue.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + auto v8Function = v8MaybeLocalValue.ToLocalChecked(); + if (v8Function->IsFunction()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + V8MaybeLocalValue v8MaybeLocalValueResult; + uint32_t valueCount = mValues == nullptr ? 0 : jniEnv->GetArrayLength(mValues); + if (valueCount > 0) { + auto umValuesPointer = Javet::Converter::ToV8Values(jniEnv, v8Context, mValues); + v8MaybeLocalValueResult = v8Function.As()->Call(v8Context, v8LocalObject, valueCount, umValuesPointer.get()); + } + else { + v8MaybeLocalValueResult = v8Function.As()->Call(v8Context, v8LocalObject, 0, nullptr); + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + else if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); + } + } + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSet +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobjectArray keysAndValues) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + auto length = jniEnv->GetArrayLength(keysAndValues); + if (length == 0 || length % 2 != 0) { + return false; + } + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8LocalObject = v8LocalValue.As(); + for (int i = 0; i < length; i += 2) { + auto jobjectValue = jniEnv->GetObjectArrayElement(keysAndValues, i + 1); + auto v8LocalValueValue = Javet::Converter::ToV8Value(jniEnv, v8Context, jobjectValue); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + auto jobjectKey = jniEnv->GetObjectArrayElement(keysAndValues, i); + if (!Javet::V8ValueObject::objectSet( + jniEnv, + v8Runtime, + v8Context, + v8LocalObject, + jobjectKey, + v8LocalValueValue)) { + return false; + } + } + return true; + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetAccessor +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject mPropertyName, jobject mContextGetter, jobject mContextSetter) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + V8MaybeBool v8MaybeBool = v8::Just(false); + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + V8LocalName v8LocalName; + if (Javet::Converter::IsV8ValueString(jniEnv, mPropertyName)) { + v8LocalName = Javet::Converter::ToV8Value(jniEnv, v8Context, mPropertyName).As(); + } + else if (Javet::Converter::IsV8ValueSymbol(jniEnv, mPropertyName)) { + v8LocalName = Javet::Converter::ToV8Value(jniEnv, v8Context, mPropertyName).As(); + } + else { + return false; + } + if (mContextGetter == nullptr) { + v8MaybeBool = v8LocalObject.As()->SetAccessor(v8Context, v8LocalName, nullptr); + } + else { + auto v8LocalArrayContext = v8::Array::New(v8Context->GetIsolate(), 2); + auto javetCallbackContextReferencePointer = new Javet::Callback::JavetCallbackContextReference(jniEnv, mContextGetter); + INCREASE_COUNTER(Javet::Monitor::CounterType::NewJavetCallbackContextReference); + auto v8LocalContextGetterHandle = v8::BigInt::New(v8Context->GetIsolate(), TO_NATIVE_INT_64(javetCallbackContextReferencePointer)); + javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer = + new V8PersistentBigInt(v8Context->GetIsolate(), v8LocalContextGetterHandle); + INCREASE_COUNTER(Javet::Monitor::CounterType::NewPersistentCallbackContextReference); + javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer->SetWeak( + javetCallbackContextReferencePointer, Javet::Callback::JavetCloseWeakCallbackContextHandle, v8::WeakCallbackType::kParameter); + auto maybeResult = v8LocalArrayContext->Set(v8Context, 0, v8LocalContextGetterHandle); + v8::AccessorNameGetterCallback getter = Javet::Callback::JavetPropertyGetterCallback; + v8::AccessorNameSetterCallback setter = nullptr; + if (mContextSetter != nullptr) { + javetCallbackContextReferencePointer = new Javet::Callback::JavetCallbackContextReference(jniEnv, mContextSetter); + INCREASE_COUNTER(Javet::Monitor::CounterType::NewJavetCallbackContextReference); + auto v8LocalContextSetterHandle = v8::BigInt::New(v8Context->GetIsolate(), TO_NATIVE_INT_64(javetCallbackContextReferencePointer)); + javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer = + new V8PersistentBigInt(v8Context->GetIsolate(), v8LocalContextSetterHandle); + INCREASE_COUNTER(Javet::Monitor::CounterType::NewPersistentCallbackContextReference); + javetCallbackContextReferencePointer->v8PersistentCallbackContextHandlePointer->SetWeak( + javetCallbackContextReferencePointer, Javet::Callback::JavetCloseWeakCallbackContextHandle, v8::WeakCallbackType::kParameter); + maybeResult = v8LocalArrayContext->Set(v8Context, 1, v8LocalContextSetterHandle); + setter = Javet::Callback::JavetPropertySetterCallback; + } + v8MaybeBool = v8LocalObject.As()->SetAccessor(v8Context, v8LocalName, getter, setter, v8LocalArrayContext); + } + } + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + return v8MaybeBool.FromMaybe(false); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetBoolean +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jboolean value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_OBJECT(v8ValueType)) { + auto v8LocalObject = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Boolean(v8Context, value); + return Javet::V8ValueObject::objectSet(jniEnv, v8Runtime, v8Context, v8LocalObject, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetDouble +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jdouble value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_OBJECT(v8ValueType)) { + auto v8LocalObject = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Double(v8Context, value); + return Javet::V8ValueObject::objectSet(jniEnv, v8Runtime, v8Context, v8LocalObject, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetInteger +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jint value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_OBJECT(v8ValueType)) { + auto v8LocalObject = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Integer(v8Context, value); + return Javet::V8ValueObject::objectSet(jniEnv, v8Runtime, v8Context, v8LocalObject, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetLong +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jlong value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_OBJECT(v8ValueType)) { + auto v8LocalObject = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Long(v8Context, value); + return Javet::V8ValueObject::objectSet(jniEnv, v8Runtime, v8Context, v8LocalObject, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetNull +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Null(v8Context); + return Javet::V8ValueObject::objectSet(jniEnv, v8Runtime, v8Context, v8LocalObject, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetPrivateProperty +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jstring mKey, jobject mValue) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + auto v8LocalStringKey = Javet::Converter::ToV8String(jniEnv, v8Context, mKey); + auto v8LocalPrivateKey = v8::Private::ForApi(v8Context->GetIsolate(), v8LocalStringKey); + auto v8LocalPrivateValue = Javet::Converter::ToV8Value(jniEnv, v8Context, mValue); + auto v8MaybeBool = v8LocalValue.As()->SetPrivate(v8Context, v8LocalPrivateKey, v8LocalPrivateValue); + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetProperty +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jobject value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + V8MaybeBool v8MaybeBool = v8::Just(false); + auto v8LocalObject = v8LocalValue.As(); + auto v8ValueValue = Javet::Converter::ToV8Value(jniEnv, v8Context, value); + if (Javet::Converter::IsV8ValueInteger(jniEnv, key)) { + jint integerKey = Javet::Converter::ToJavaIntegerFromV8ValueInteger(jniEnv, key); + v8MaybeBool = v8LocalObject->Set(v8Context, integerKey, v8ValueValue); + } + else { + auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + if (!v8ValueKey.IsEmpty()) { + v8MaybeBool = v8LocalObject->Set(v8Context, v8ValueKey, v8ValueValue); + } + } + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetPrototype +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jlong v8ValueHandlePrototype) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + auto v8PersistentObjectPrototypePointer = TO_V8_PERSISTENT_VALUE_POINTER(v8ValueHandlePrototype); + auto v8LocalObjectPrototype = v8PersistentObjectPrototypePointer->Get(v8Context->GetIsolate()); + auto v8MaybeBool = v8LocalObject->SetPrototype(v8Context, v8LocalObjectPrototype); + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetString +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key, jstring value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + auto v8LocalValueValue = value == nullptr + ? Javet::Converter::ToV8Null(v8Context).As() + : Javet::Converter::ToV8String(jniEnv, v8Context, value).As(); + return Javet::V8ValueObject::objectSet(jniEnv, v8Runtime, v8Context, v8LocalObject, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_objectSetUndefined +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + auto v8LocalValueValue = Javet::Converter::ToV8Undefined(v8Context); + return Javet::V8ValueObject::objectSet(jniEnv, v8Runtime, v8Context, v8LocalObject, key, v8LocalValueValue); + } + return false; +} + +JNIEXPORT jstring JNICALL Java_com_caoccao_javet_interop_V8Native_objectToProtoString +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + V8MaybeLocalString v8MaybeLocalString; + if (v8LocalValue->IsObject()) { + auto v8LocalObject = v8LocalValue.As(); + v8MaybeLocalString = v8LocalObject->ObjectProtoToString(v8Context); + if (v8MaybeLocalString.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + } + V8LocalString v8LocalString = v8MaybeLocalString.IsEmpty() ? V8LocalString() : v8MaybeLocalString.ToLocalChecked(); + return Javet::Converter::ToJavaString(jniEnv, v8Context, v8LocalString); +} diff --git a/cpp/jni/javet_jni_promise.cpp b/cpp/jni/javet_jni_promise.cpp new file mode 100644 index 000000000..394e12278 --- /dev/null +++ b/cpp/jni/javet_jni_promise.cpp @@ -0,0 +1,166 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseCreate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8MaybeLocalPromiseResolver = v8::Promise::Resolver::New(v8Context); + if (v8MaybeLocalPromiseResolver.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context, "Promise resolver allocation failed")) { + return nullptr; + } + } + else { + auto v8LocalPromiseResolver = v8MaybeLocalPromiseResolver.ToLocalChecked(); + if (!v8LocalPromiseResolver.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalPromiseResolver); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_promiseGetState +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROMISE(v8ValueType)) { + return (jint)v8LocalValue.As()->State(); + } + return -1; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseCatch +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jlong v8ValueFunctionHandle) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROMISE(v8ValueType)) { + auto v8PersistentFunctionPointer = TO_V8_PERSISTENT_FUNCTION_POINTER(v8ValueFunctionHandle); + auto v8LocalFunction = v8PersistentFunctionPointer->Get(v8Context->GetIsolate()); + auto v8MaybeLocalValueResult = v8LocalValue.As()->Catch(v8Context, v8LocalFunction); + if (v8MaybeLocalValueResult.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseGetResult +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROMISE(v8ValueType)) { + auto v8LocalPromise = v8LocalValue.As(); + if (v8LocalPromise->State() != v8::Promise::PromiseState::kPending) { + auto v8ValueResult = v8LocalPromise->Result(); + if (v8ValueResult.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8ValueResult); + } + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_promiseHasHandler +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROMISE(v8ValueType)) { + return v8LocalValue.As()->HasHandler(); + } + return false; +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_promiseMarkAsHandled +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROMISE(v8ValueType)) { + v8LocalValue.As()->MarkAsHandled(); + } +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseThen +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jlong v8ValueFunctionFulfilledHandle, jlong v8ValueFunctionRejectedHandle) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROMISE(v8ValueType)) { + auto v8PersistentFunctionFulfilledPointer = TO_V8_PERSISTENT_FUNCTION_POINTER(v8ValueFunctionFulfilledHandle); + auto v8LocalFunctionFulfilled = v8PersistentFunctionFulfilledPointer->Get(v8Context->GetIsolate()); + V8MaybeLocalPromise v8MaybeLocalValueResult; + if (v8ValueFunctionRejectedHandle == 0L) { + v8MaybeLocalValueResult = v8LocalValue.As()->Then(v8Context, v8LocalFunctionFulfilled); + } + else { + auto v8PersistentFunctionRejectedPointer = TO_V8_PERSISTENT_FUNCTION_POINTER(v8ValueFunctionRejectedHandle); + auto v8LocalFunctionRejected = v8PersistentFunctionRejectedPointer->Get(v8Context->GetIsolate()); + v8MaybeLocalValueResult = v8LocalValue.As()->Then(v8Context, v8LocalFunctionFulfilled, v8LocalFunctionRejected); + } + if (v8MaybeLocalValueResult.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context)) { + return nullptr; + } + } + else { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_promiseGetPromise +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROMISE(v8ValueType)) { + auto v8LocalPromiseResolver = v8LocalValue.As(); + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalPromiseResolver->GetPromise()); + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_promiseReject +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE_WITH_UNIQUE_LOCKER(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROMISE(v8ValueType)) { + auto v8LocalPromiseResolver = v8LocalValue.As(); + auto v8MaybeBool = v8LocalPromiseResolver->Reject(v8Context, Javet::Converter::ToV8Value(jniEnv, v8Context, value)); + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_promiseResolve +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE_WITH_UNIQUE_LOCKER(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROMISE(v8ValueType)) { + auto v8LocalPromiseResolver = v8LocalValue.As(); + auto v8MaybeBool = v8LocalPromiseResolver->Resolve(v8Context, Javet::Converter::ToV8Value(jniEnv, v8Context, value)); + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + return v8MaybeBool.FromMaybe(false); + } + return false; +} diff --git a/cpp/jni/javet_jni_proxy.cpp b/cpp/jni/javet_jni_proxy.cpp new file mode 100644 index 000000000..970cd1ed9 --- /dev/null +++ b/cpp/jni/javet_jni_proxy.cpp @@ -0,0 +1,75 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_proxyCreate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jobject mTarget) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + V8LocalObject v8LocalObjectTaget = mTarget == nullptr + ? v8::Object::New(v8Context->GetIsolate()) + : Javet::Converter::ToV8Value(jniEnv, v8Context, mTarget).As(); + auto v8LocalObjectHandler = v8::Object::New(v8Context->GetIsolate()); + auto v8MaybeLocalProxy = v8::Proxy::New(v8Context, v8LocalObjectTaget, v8LocalObjectHandler); + if (v8MaybeLocalProxy.IsEmpty()) { + if (Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context, "Proxy allocation failed")) { + return nullptr; + } + } + else { + auto v8LocalProxy = v8MaybeLocalProxy.ToLocalChecked(); + if (!v8LocalProxy.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalProxy); + } + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_proxyGetHandler +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROXY(v8ValueType)) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalValue.As()->GetHandler()); + } + return nullptr; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_proxyGetTarget +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROXY(v8ValueType)) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalValue.As()->GetTarget()); + } + return nullptr; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_proxyIsRevoked +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROXY(v8ValueType)) { + return v8LocalValue.As()->IsRevoked(); + } + return false; +} + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_proxyRevoke +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_PROXY(v8ValueType)) { + v8LocalValue.As()->Revoke(); + } +} diff --git a/cpp/jni/javet_jni_script.cpp b/cpp/jni/javet_jni_script.cpp new file mode 100644 index 000000000..a28f23e78 --- /dev/null +++ b/cpp/jni/javet_jni_script.cpp @@ -0,0 +1,128 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_scriptCompile +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mScript, jbyteArray mCachedData, jboolean mResultRequired, + jstring mResourceName, jint mResourceLineOffset, jint mResourceColumnOffset, jint mScriptId, jboolean mIsWASM, jboolean mIsModule) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + if (!mIsModule) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto umScript = Javet::Converter::ToV8String(jniEnv, v8Context, mScript); + auto scriptOriginPointer = Javet::Converter::ToV8ScriptOringinPointer( + jniEnv, v8Context, mResourceName, mResourceLineOffset, mResourceColumnOffset, mScriptId, mIsWASM, mIsModule); + v8::MaybeLocal v8MaybeLocalScript; + if (mCachedData) { + V8ScriptCompilerSource scriptSource( + umScript, *scriptOriginPointer.get(), Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + V8InternalDisallowCompilation v8InternalDisallowCompilation(v8InternalIsolate); + v8MaybeLocalScript = v8::ScriptCompiler::Compile(v8Context, &scriptSource, v8::ScriptCompiler::kConsumeCodeCache); + LOG_DEBUG("Script cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); + } + else { + V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); + v8MaybeLocalScript = v8::ScriptCompiler::Compile(v8Context, &scriptSource); + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + else if (mResultRequired && !v8MaybeLocalScript.IsEmpty()) { + return Javet::Converter::ToExternalV8Script( + jniEnv, v8Runtime, v8Context, v8MaybeLocalScript.ToLocalChecked()); + } + } + return nullptr; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_scriptExecute +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mScript, jbyteArray mCachedData, jboolean mResultRequired, + jstring mResourceName, jint mResourceLineOffset, jint mResourceColumnOffset, jint mScriptId, jboolean mIsWASM) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto umScript = Javet::Converter::ToV8String(jniEnv, v8Context, mScript); + auto scriptOriginPointer = Javet::Converter::ToV8ScriptOringinPointer( + jniEnv, v8Context, mResourceName, mResourceLineOffset, mResourceColumnOffset, mScriptId, mIsWASM, false); + v8::MaybeLocal v8MaybeLocalScript; + if (mCachedData) { + V8ScriptCompilerSource scriptSource( + umScript, *scriptOriginPointer.get(), Javet::Converter::ToCachedDataPointer(jniEnv, mCachedData)); + auto v8InternalIsolate = reinterpret_cast(v8Context->GetIsolate()); + V8InternalDisallowCompilation v8InternalDisallowCompilation(v8InternalIsolate); + v8MaybeLocalScript = v8::ScriptCompiler::Compile(v8Context, &scriptSource, v8::ScriptCompiler::kConsumeCodeCache); + LOG_DEBUG("Script cache is " << (scriptSource.GetCachedData()->rejected ? "rejected" : "accepted") << "."); + } + else { + V8ScriptCompilerSource scriptSource(umScript, *scriptOriginPointer.get()); + v8MaybeLocalScript = v8::ScriptCompiler::Compile(v8Context, &scriptSource); + } + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetCompilationException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + else if (!v8MaybeLocalScript.IsEmpty()) { + auto compliedScript = v8MaybeLocalScript.ToLocalChecked(); + auto v8MaybeLocalValueResult = compliedScript->Run(v8Context); + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { + Javet::Exceptions::ClearJNIException(jniEnv); + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); + } + } + Javet::Exceptions::ClearJNIException(jniEnv); + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jbyteArray JNICALL Java_com_caoccao_javet_interop_V8Native_scriptGetCachedData +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + if (IS_V8_SCRIPT(v8ValueType)) { + RUNTIME_AND_SCRIPT_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (!v8LocalScript.IsEmpty()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + std::unique_ptr cachedDataPointer; + cachedDataPointer.reset(v8::ScriptCompiler::CreateCodeCache(v8LocalScript->GetUnboundScript())); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return nullptr; + } + if (cachedDataPointer) { + return Javet::Converter::ToJavaByteArray(jniEnv, cachedDataPointer.get()); + } + } + } + return nullptr; +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_scriptRun +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jboolean mResultRequired) { + RUNTIME_AND_SCRIPT_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (!v8LocalScript.IsEmpty()) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8MaybeLocalValueResult = v8LocalScript->Run(v8Context); + if (v8TryCatch.HasCaught()) { + return Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + } + if (mResultRequired && !v8MaybeLocalValueResult.IsEmpty()) { + Javet::Exceptions::ClearJNIException(jniEnv); + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8MaybeLocalValueResult.ToLocalChecked()); + } + } + Javet::Exceptions::ClearJNIException(jniEnv); + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} diff --git a/cpp/jni/javet_jni_set.cpp b/cpp/jni/javet_jni_set.cpp new file mode 100644 index 000000000..b04df2b33 --- /dev/null +++ b/cpp/jni/javet_jni_set.cpp @@ -0,0 +1,91 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT void JNICALL Java_com_caoccao_javet_interop_V8Native_setAdd +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_SET(v8ValueType)) { + auto v8ValueValue = Javet::Converter::ToV8Value(jniEnv, v8Context, value); + auto v8MaybeLocalSet = v8LocalValue.As()->Add(v8Context, v8ValueValue); + if (v8MaybeLocalSet.IsEmpty()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + } +} + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_setCreate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8LocalSet = v8::Set::New(v8Context->GetIsolate()); + if (!v8LocalSet.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalSet); + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setDelete +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject key) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_SET(v8ValueType)) { + auto v8ValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, key); + V8MaybeBool v8MaybeBool = v8LocalValue.As()->Delete(v8Context, v8ValueKey); + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + } + else { + return v8MaybeBool.FromMaybe(false); + } + } + return false; +} + +JNIEXPORT jint JNICALL Java_com_caoccao_javet_interop_V8Native_setGetSize +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_SET(v8ValueType)) { + return (jint)v8LocalValue.As()->Size(); + } + return 0; +} + +JNIEXPORT jboolean JNICALL Java_com_caoccao_javet_interop_V8Native_setHas +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jlong v8ValueHandle, jint v8ValueType, jobject value) { + RUNTIME_AND_VALUE_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle, v8ValueHandle); + if (IS_V8_SET(v8ValueType)) { + V8TryCatch v8TryCatch(v8Context->GetIsolate()); + auto v8LocalValueKey = Javet::Converter::ToV8Value(jniEnv, v8Context, value); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (!v8LocalValueKey.IsEmpty()) { + V8MaybeBool v8MaybeBool = v8LocalValue.As()->Has(v8Context, v8LocalValueKey); + if (v8TryCatch.HasCaught()) { + Javet::Exceptions::ThrowJavetExecutionException(jniEnv, v8Runtime, v8Context, v8TryCatch); + return false; + } + if (v8MaybeBool.IsNothing()) { + Javet::Exceptions::HandlePendingException(jniEnv, v8Runtime, v8Context); + return false; + } + return v8MaybeBool.FromMaybe(false); + } + } + return false; +} diff --git a/cpp/jni/javet_jni_symbol.cpp b/cpp/jni/javet_jni_symbol.cpp new file mode 100644 index 000000000..a496eae04 --- /dev/null +++ b/cpp/jni/javet_jni_symbol.cpp @@ -0,0 +1,29 @@ +/* + * Copyright (c) 2021-2023 caoccao.com Sam Cao + * All rights reserved. + + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + + * http://www.apache.org/licenses/LICENSE-2.0 + + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "javet_jni.h" + +JNIEXPORT jobject JNICALL Java_com_caoccao_javet_interop_V8Native_symbolCreate +(JNIEnv* jniEnv, jobject caller, jlong v8RuntimeHandle, jstring mDescription) { + RUNTIME_HANDLES_TO_OBJECTS_WITH_SCOPE(v8RuntimeHandle); + auto v8LocalStringDescription = Javet::Converter::ToV8String(jniEnv, v8Context, mDescription); + auto v8LocalSymbol = v8::Symbol::New(v8Context->GetIsolate(), v8LocalStringDescription); + if (!v8LocalSymbol.IsEmpty()) { + return v8Runtime->SafeToExternalV8Value(jniEnv, v8Context, v8LocalSymbol); + } + return Javet::Converter::ToExternalV8ValueUndefined(jniEnv, v8Runtime); +} diff --git a/cpp/jni/javet_resource_node.rc b/cpp/jni/javet_resource_node.rc index c64219342..28f9bc17e 100644 --- a/cpp/jni/javet_resource_node.rc +++ b/cpp/jni/javet_resource_node.rc @@ -61,8 +61,8 @@ LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US // VS_VERSION_INFO VERSIONINFO - FILEVERSION 2,1,2,0 - PRODUCTVERSION 2,1,2,0 + FILEVERSION 2,2,0,0 + PRODUCTVERSION 2,2,0,0 FILEFLAGSMASK 0x3fL #ifdef _DEBUG FILEFLAGS 0x1L @@ -79,12 +79,12 @@ BEGIN BEGIN VALUE "CompanyName", "caoccao.com" VALUE "FileDescription", "caoccao.com" - VALUE "FileVersion", "2.1.2.0" - VALUE "InternalName", "libjavet-node-windows-x86_64.v.2.1.2.dll" + VALUE "FileVersion", "2.2.0.0" + VALUE "InternalName", "libjavet-node-windows-x86_64.v.2.2.0.dll" VALUE "LegalCopyright", "Copyright (C) 2021" - VALUE "OriginalFilename", "libjavet-node-windows-x86_64.v.2.1.2.dll" + VALUE "OriginalFilename", "libjavet-node-windows-x86_64.v.2.2.0.dll" VALUE "ProductName", "Javet Windows" - VALUE "ProductVersion", "2.1.2.0" + VALUE "ProductVersion", "2.2.0.0" END END BLOCK "VarFileInfo" diff --git a/cpp/jni/javet_resource_v8.rc b/cpp/jni/javet_resource_v8.rc index fbf4dbd16..b19ab961f 100644 --- a/cpp/jni/javet_resource_v8.rc +++ b/cpp/jni/javet_resource_v8.rc @@ -61,8 +61,8 @@ LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US // VS_VERSION_INFO VERSIONINFO - FILEVERSION 2,1,2,0 - PRODUCTVERSION 2,1,2,0 + FILEVERSION 2,2,0,0 + PRODUCTVERSION 2,2,0,0 FILEFLAGSMASK 0x3fL #ifdef _DEBUG FILEFLAGS 0x1L @@ -79,12 +79,12 @@ BEGIN BEGIN VALUE "CompanyName", "caoccao.com" VALUE "FileDescription", "caoccao.com" - VALUE "FileVersion", "2.1.2.0" - VALUE "InternalName", "libjavet-v8-windows-x86_64.v.2.1.2.dll" + VALUE "FileVersion", "2.2.0.0" + VALUE "InternalName", "libjavet-v8-windows-x86_64.v.2.2.0.dll" VALUE "LegalCopyright", "Copyright (C) 2021" - VALUE "OriginalFilename", "libjavet-v8-windows-x86_64.v.2.1.2.dll" + VALUE "OriginalFilename", "libjavet-v8-windows-x86_64.v.2.2.0.dll" VALUE "ProductName", "Javet Windows" - VALUE "ProductVersion", "2.1.2.0" + VALUE "ProductVersion", "2.2.0.0" END END BLOCK "VarFileInfo" diff --git a/docker/android/base.Dockerfile b/docker/android/base.Dockerfile index 6d8c9b66b..aaf22d925 100644 --- a/docker/android/base.Dockerfile +++ b/docker/android/base.Dockerfile @@ -13,9 +13,9 @@ # See the License for the specific language governing permissions and # limitations under the License. -# Usage: docker build -t sjtucaocao/javet-android:2.1.2 -f docker/android/base.Dockerfile . +# Usage: docker build -t sjtucaocao/javet-android:2.2.0 -f docker/android/base.Dockerfile . -ARG JAVET_V8_VERSION=11.3.244.8 +ARG JAVET_V8_VERSION=11.4.183.14 FROM ubuntu:20.04 WORKDIR / diff --git a/docker/android/build.Dockerfile b/docker/android/build.Dockerfile index 6cdedeb2c..58bb65705 100644 --- a/docker/android/build.Dockerfile +++ b/docker/android/build.Dockerfile @@ -15,7 +15,7 @@ # Usage: docker build -t javet-android:local -f docker/android/build.Dockerfile . -FROM sjtucaocao/javet-android:2.1.2 +FROM sjtucaocao/javet-android:2.2.0 WORKDIR / # Copy Javet diff --git a/docker/linux-arm64/base_all_in_one.Dockerfile b/docker/linux-arm64/base_all_in_one.Dockerfile index 988866a26..e6e019ba7 100644 --- a/docker/linux-arm64/base_all_in_one.Dockerfile +++ b/docker/linux-arm64/base_all_in_one.Dockerfile @@ -13,10 +13,10 @@ # See the License for the specific language governing permissions and # limitations under the License. -# Usage: docker build -t sjtucaocao/javet-arm64:2.1.2 -f docker/linux-arm64/base_all_in_one.Dockerfile . +# Usage: docker build -t sjtucaocao/javet-arm64:2.2.0 -f docker/linux-arm64/base_all_in_one.Dockerfile . ARG JAVET_NODE_VERSION=18.15.0 -ARG JAVET_V8_VERSION=11.3.244.8 +ARG JAVET_V8_VERSION=11.4.183.14 FROM ubuntu:20.04 WORKDIR / diff --git a/docker/linux-arm64/base_gradle.Dockerfile b/docker/linux-arm64/base_gradle.Dockerfile index 233bca72b..085d9e3b8 100644 --- a/docker/linux-arm64/base_gradle.Dockerfile +++ b/docker/linux-arm64/base_gradle.Dockerfile @@ -14,7 +14,7 @@ # limitations under the License. # Usage: docker build \ -# -t sjtucaocao/javet:arm64-2.1.2 \ +# -t sjtucaocao/javet:arm64-2.2.0 \ # --build-arg JAVET_REPO=sjtucaocao/javet \ # -f docker/linux-arm64/base_gradle.Dockerfile . diff --git a/docker/linux-arm64/base_v8.Dockerfile b/docker/linux-arm64/base_v8.Dockerfile index b3927a031..8c4a30964 100644 --- a/docker/linux-arm64/base_v8.Dockerfile +++ b/docker/linux-arm64/base_v8.Dockerfile @@ -14,13 +14,13 @@ # limitations under the License. # Usage: docker build \ -# -t sjtucaocao/javet:arm64-base-v8_11.3.244.8 \ +# -t sjtucaocao/javet:arm64-base-v8_11.4.183.14 \ # --build-arg JAVET_REPO=sjtucaocao/javet \ -# --build-arg JAVET_V8_VERSION=11.3.244.8 \ +# --build-arg JAVET_V8_VERSION=11.4.183.14 \ # -f docker/linux-arm64/base_v8.Dockerfile . ARG JAVET_REPO=sjtucaocao/javet -ARG JAVET_V8_VERSION=11.3.244.8 +ARG JAVET_V8_VERSION=11.4.183.14 FROM ${JAVET_REPO}:arm64-base-jvm diff --git a/docker/linux-arm64/build_artifact.Dockerfile b/docker/linux-arm64/build_artifact.Dockerfile index f8578c139..c98fb9203 100644 --- a/docker/linux-arm64/build_artifact.Dockerfile +++ b/docker/linux-arm64/build_artifact.Dockerfile @@ -18,13 +18,13 @@ # --build-arg JAVET_REPO=sjtucaocao/javet \ # --build-arg JAVET_NODE_VERSION=18.12.1 \ # --build-arg JAVET_V8_VERSION=10.8.168.20 \ -# --build-arg JAVET_VERSION=2.1.2 \ +# --build-arg JAVET_VERSION=2.2.0 \ # -f docker/linux-arm64/build_artifact.Dockerfile . ARG JAVET_REPO=sjtucaocao/javet ARG JAVET_NODE_VERSION=18.12.1 ARG JAVET_V8_VERSION=10.8.168.20 -ARG JAVET_VERSION=2.1.2 +ARG JAVET_VERSION=2.2.0 FROM ${JAVET_REPO}:arm64-base-node_${JAVET_NODE_VERSION} as base-node diff --git a/docker/linux-x86_64/base_all_in_one.Dockerfile b/docker/linux-x86_64/base_all_in_one.Dockerfile index a6172da9c..f435cb6f7 100644 --- a/docker/linux-x86_64/base_all_in_one.Dockerfile +++ b/docker/linux-x86_64/base_all_in_one.Dockerfile @@ -13,10 +13,10 @@ # See the License for the specific language governing permissions and # limitations under the License. -# Usage: docker build -t sjtucaocao/javet:2.1.2 -f docker/linux-x86_64/base_all_in_one.Dockerfile . +# Usage: docker build -t sjtucaocao/javet:2.2.0 -f docker/linux-x86_64/base_all_in_one.Dockerfile . ARG JAVET_NODE_VERSION=18.16.0 -ARG JAVET_V8_VERSION=11.3.244.8 +ARG JAVET_V8_VERSION=11.4.183.14 FROM ubuntu:20.04 WORKDIR / diff --git a/docker/linux-x86_64/base_gradle.Dockerfile b/docker/linux-x86_64/base_gradle.Dockerfile index f75cd1766..ae2d98216 100644 --- a/docker/linux-x86_64/base_gradle.Dockerfile +++ b/docker/linux-x86_64/base_gradle.Dockerfile @@ -14,7 +14,7 @@ # limitations under the License. # Usage: docker build \ -# -t sjtucaocao/javet:x86_64-2.1.2 \ +# -t sjtucaocao/javet:x86_64-2.2.0 \ # --build-arg JAVET_REPO=sjtucaocao/javet \ # -f docker/linux-x86_64/base_gradle.Dockerfile . diff --git a/docker/linux-x86_64/base_v8.Dockerfile b/docker/linux-x86_64/base_v8.Dockerfile index 63baf61f5..be5e7ac29 100644 --- a/docker/linux-x86_64/base_v8.Dockerfile +++ b/docker/linux-x86_64/base_v8.Dockerfile @@ -14,13 +14,13 @@ # limitations under the License. # Usage: docker build \ -# -t sjtucaocao/javet:x86_64-base-v8_11.3.244.8 \ +# -t sjtucaocao/javet:x86_64-base-v8_11.4.183.14 \ # --build-arg JAVET_REPO=sjtucaocao/javet \ -# --build-arg JAVET_V8_VERSION=11.3.244.8 \ +# --build-arg JAVET_V8_VERSION=11.4.183.14 \ # -f docker/linux-x86_64/base_v8.Dockerfile . ARG JAVET_REPO=sjtucaocao/javet -ARG JAVET_V8_VERSION=11.3.244.8 +ARG JAVET_V8_VERSION=11.4.183.14 FROM ${JAVET_REPO}:x86_64-base-jvm diff --git a/docker/linux-x86_64/build_all_in_one.Dockerfile b/docker/linux-x86_64/build_all_in_one.Dockerfile index 6f0ce797a..565027de8 100644 --- a/docker/linux-x86_64/build_all_in_one.Dockerfile +++ b/docker/linux-x86_64/build_all_in_one.Dockerfile @@ -15,7 +15,7 @@ # Usage: docker build -t javet:local -f docker/linux-x86_64/build_all_in_one.Dockerfile . -FROM sjtucaocao/javet:2.1.2 +FROM sjtucaocao/javet:2.2.0 WORKDIR / # Copy Javet diff --git a/docker/linux-x86_64/build_artifact.Dockerfile b/docker/linux-x86_64/build_artifact.Dockerfile index 4d1c7dc47..a597defbd 100644 --- a/docker/linux-x86_64/build_artifact.Dockerfile +++ b/docker/linux-x86_64/build_artifact.Dockerfile @@ -18,13 +18,13 @@ # --build-arg JAVET_REPO=sjtucaocao/javet \ # --build-arg JAVET_NODE_VERSION=18.12.1 \ # --build-arg JAVET_V8_VERSION=10.8.168.20 \ -# --build-arg JAVET_VERSION=2.1.2 \ +# --build-arg JAVET_VERSION=2.2.0 \ # -f docker/linux-x86_64/build_artifact.Dockerfile . ARG JAVET_REPO=sjtucaocao/javet ARG JAVET_NODE_VERSION=18.12.1 ARG JAVET_V8_VERSION=10.8.168.20 -ARG JAVET_VERSION=2.1.2 +ARG JAVET_VERSION=2.2.0 FROM ${JAVET_REPO}:x86_64-base-node_${JAVET_NODE_VERSION} as base-v8 diff --git a/docker/windows-x86_64/base.Dockerfile b/docker/windows-x86_64/base.Dockerfile index 39d7e60b3..de64c00da 100644 --- a/docker/windows-x86_64/base.Dockerfile +++ b/docker/windows-x86_64/base.Dockerfile @@ -29,10 +29,10 @@ # The following dockerfile has been out of date because it still uses # Visual Studio 2019 Community. Please contact the maintainer if you want an upgrade. -# Usage: docker build -t sjtucaocao/javet-windows:2.1.2 -m 4G -f docker/windows-x86_64/base.Dockerfile . +# Usage: docker build -t sjtucaocao/javet-windows:2.2.0 -m 4G -f docker/windows-x86_64/base.Dockerfile . ARG JAVET_NODE_VERSION=18.16.0 -ARG JAVET_V8_VERSION=11.3.244.8 +ARG JAVET_V8_VERSION=11.4.183.14 # https://hub.docker.com/_/microsoft-windows FROM mcr.microsoft.com/windows:20H2-amd64 diff --git a/docker/windows-x86_64/build.Dockerfile b/docker/windows-x86_64/build.Dockerfile index 39dbadaa8..c49216386 100644 --- a/docker/windows-x86_64/build.Dockerfile +++ b/docker/windows-x86_64/build.Dockerfile @@ -15,7 +15,7 @@ # Usage: docker build -t javet:local -f docker/windows-x86_64/build.Dockerfile . -FROM sjtucaocao/javet-windows:2.1.2 +FROM sjtucaocao/javet-windows:2.2.0 SHELL ["cmd", "/S", "/C"] WORKDIR / diff --git a/docs/_static/documentation_options.js b/docs/_static/documentation_options.js index d379d348e..9c0e34357 100644 --- a/docs/_static/documentation_options.js +++ b/docs/_static/documentation_options.js @@ -1,6 +1,6 @@ var DOCUMENTATION_OPTIONS = { URL_ROOT: document.getElementById("documentation_options").getAttribute('data-url_root'), - VERSION: '2.1.2', + VERSION: '2.2.0', LANGUAGE: 'en, zh-CN', COLLAPSE_INDEX: false, BUILDER: 'html', diff --git a/docs/conf.py b/docs/conf.py index 42c12beda..29ebb121a 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -22,7 +22,7 @@ author = 'Sam Cao' # The full version, including alpha/beta/rc tags -release = '2.1.2' +release = '2.2.0' # -- General configuration --------------------------------------------------- diff --git a/docs/development/build.html b/docs/development/build.html index 33c010d8d..956523b9f 100644 --- a/docs/development/build.html +++ b/docs/development/build.html @@ -5,7 +5,7 @@ - Build Javet - Javet 2.1.2 documentation + Build Javet - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
@@ -150,7 +150,7 @@
- Javet 2.1.2 documentation + Javet 2.2.0 documentation
@@ -150,7 +150,7 @@
- Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/development/build_javet_with_docker.html b/docs/development/build_javet_with_docker.html index 9cb42fa36..c54efe3f4 100644 --- a/docs/development/build_javet_with_docker.html +++ b/docs/development/build_javet_with_docker.html @@ -5,7 +5,7 @@ - Build Javet with Docker - Javet 2.1.2 documentation + Build Javet with Docker - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/development/build_javet_with_pre_built_binaries.html b/docs/development/build_javet_with_pre_built_binaries.html index d73b9b315..d4a3f7fc3 100644 --- a/docs/development/build_javet_with_pre_built_binaries.html +++ b/docs/development/build_javet_with_pre_built_binaries.html @@ -5,7 +5,7 @@ - Build Javet with Pre-built Binaries - Javet 2.1.2 documentation + Build Javet with Pre-built Binaries - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/development/debug_with_chrome_developer_tools.html b/docs/development/debug_with_chrome_developer_tools.html index 8640e5836..83e6045bd 100644 --- a/docs/development/debug_with_chrome_developer_tools.html +++ b/docs/development/debug_with_chrome_developer_tools.html @@ -2,10 +2,10 @@ - + - Debug with Chrome Developer Tools - Javet 2.1.2 documentation + Debug with Chrome Developer Tools - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • @@ -385,14 +386,14 @@

    Customization - +
    Previous
    -
    Javet Design
    +
    Javet Performance
    diff --git a/docs/development/design.html b/docs/development/design.html index b3b76e9e1..937bcbec1 100644 --- a/docs/development/design.html +++ b/docs/development/design.html @@ -2,10 +2,10 @@ - + - Javet Design - Javet 2.1.2 documentation + Javet Design - Javet 2.2.0 documentation @@ -124,7 +124,7 @@

    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • @@ -497,12 +498,12 @@

    Memory Leak Detection
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • @@ -322,6 +323,7 @@

    DevelopmentMemory Leak Detection +
  • Javet Performance
  • Debug with Chrome Developer Tools
  • @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/background/history_with_j2v8.html b/docs/faq/background/history_with_j2v8.html index e928ef2dd..de2312ea5 100644 --- a/docs/faq/background/history_with_j2v8.html +++ b/docs/faq/background/history_with_j2v8.html @@ -5,7 +5,7 @@ - History with J2V8 - Javet 2.1.2 documentation + History with J2V8 - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/background/index.html b/docs/faq/background/index.html index ec5e1cdc6..41f69ad59 100644 --- a/docs/faq/background/index.html +++ b/docs/faq/background/index.html @@ -5,7 +5,7 @@ - Background - Javet 2.1.2 documentation + Background - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/background/what_is_the_motivation.html b/docs/faq/background/what_is_the_motivation.html index 24c2a98d2..62079e08c 100644 --- a/docs/faq/background/what_is_the_motivation.html +++ b/docs/faq/background/what_is_the_motivation.html @@ -5,7 +5,7 @@ - What is the Motivation? - Javet 2.1.2 documentation + What is the Motivation? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/development/how_to_think_in_javet.html b/docs/faq/development/how_to_think_in_javet.html index 4f313e35c..64c428700 100644 --- a/docs/faq/development/how_to_think_in_javet.html +++ b/docs/faq/development/how_to_think_in_javet.html @@ -5,7 +5,7 @@ - How to Think in Javet? - Javet 2.1.2 documentation + How to Think in Javet? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/development/index.html b/docs/faq/development/index.html index 7ed28e73d..7def417b6 100644 --- a/docs/faq/development/index.html +++ b/docs/faq/development/index.html @@ -5,7 +5,7 @@ - Development - Javet 2.1.2 documentation + Development - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/development/where_are_es6_api_in_v8_mode.html b/docs/faq/development/where_are_es6_api_in_v8_mode.html index ee3efe204..63a1aeb24 100644 --- a/docs/faq/development/where_are_es6_api_in_v8_mode.html +++ b/docs/faq/development/where_are_es6_api_in_v8_mode.html @@ -5,7 +5,7 @@ - Where are ES6 API in V8 Mode? - Javet 2.1.2 documentation + Where are ES6 API in V8 Mode? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/development/where_are_the_examples.html b/docs/faq/development/where_are_the_examples.html index 429637f38..04f2ed666 100644 --- a/docs/faq/development/where_are_the_examples.html +++ b/docs/faq/development/where_are_the_examples.html @@ -5,7 +5,7 @@ - Where are the Examples? - Javet 2.1.2 documentation + Where are the Examples? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/development/why_is_the_inspector_disabled_in_node_js_mode.html b/docs/faq/development/why_is_the_inspector_disabled_in_node_js_mode.html index 8ba875689..5bff3427b 100644 --- a/docs/faq/development/why_is_the_inspector_disabled_in_node_js_mode.html +++ b/docs/faq/development/why_is_the_inspector_disabled_in_node_js_mode.html @@ -5,7 +5,7 @@ - Why is the Inspector Disabled in Node.js Mode? - Javet 2.1.2 documentation + Why is the Inspector Disabled in Node.js Mode? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/environment/can_javet_support_legacy_linux.html b/docs/faq/environment/can_javet_support_legacy_linux.html index 001ac1174..7d9ae1b6b 100644 --- a/docs/faq/environment/can_javet_support_legacy_linux.html +++ b/docs/faq/environment/can_javet_support_legacy_linux.html @@ -5,7 +5,7 @@ - Can Javet Support Legacy Linux? - Javet 2.1.2 documentation + Can Javet Support Legacy Linux? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/environment/can_javet_support_mac.html b/docs/faq/environment/can_javet_support_mac.html index 74f14daeb..2fb8dfac9 100644 --- a/docs/faq/environment/can_javet_support_mac.html +++ b/docs/faq/environment/can_javet_support_mac.html @@ -5,7 +5,7 @@ - Can Javet Support Mac? - Javet 2.1.2 documentation + Can Javet Support Mac? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/environment/index.html b/docs/faq/environment/index.html index 9fd257c88..09b57a90f 100644 --- a/docs/faq/environment/index.html +++ b/docs/faq/environment/index.html @@ -5,7 +5,7 @@ - Environment - Javet 2.1.2 documentation + Environment - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/index.html b/docs/faq/index.html index 9e5037e59..98286968f 100644 --- a/docs/faq/index.html +++ b/docs/faq/index.html @@ -2,10 +2,10 @@ - + - FAQ - Javet 2.1.2 documentation + FAQ - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • @@ -336,14 +337,14 @@

    FAQ - +
    Previous
    -
    Release Notes 2.1.x
    +
    Release Notes 2.2.x
    diff --git a/docs/faq/troubleshooting/a_dynamic_link_library_dll_initialization_routine_failed.html b/docs/faq/troubleshooting/a_dynamic_link_library_dll_initialization_routine_failed.html index e23afee5b..d5ec587e6 100644 --- a/docs/faq/troubleshooting/a_dynamic_link_library_dll_initialization_routine_failed.html +++ b/docs/faq/troubleshooting/a_dynamic_link_library_dll_initialization_routine_failed.html @@ -5,7 +5,7 @@ - A dynamic link library (DLL) initialization routine failed - Javet 2.1.2 documentation + A dynamic link library (DLL) initialization routine failed - Javet 2.2.0 documentation @@ -124,7 +124,7 @@

    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/troubleshooting/can_i18n_be_supported.html b/docs/faq/troubleshooting/can_i18n_be_supported.html index 888737fe5..03b80620f 100644 --- a/docs/faq/troubleshooting/can_i18n_be_supported.html +++ b/docs/faq/troubleshooting/can_i18n_be_supported.html @@ -5,7 +5,7 @@ - Can i18n be Supported? - Javet 2.1.2 documentation + Can i18n be Supported? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/troubleshooting/can_i_debug_javet_in_chrome_dev_tools.html b/docs/faq/troubleshooting/can_i_debug_javet_in_chrome_dev_tools.html index 0928f7363..54624299a 100644 --- a/docs/faq/troubleshooting/can_i_debug_javet_in_chrome_dev_tools.html +++ b/docs/faq/troubleshooting/can_i_debug_javet_in_chrome_dev_tools.html @@ -5,7 +5,7 @@ - Can I Debug Javet in Chrome DevTools? - Javet 2.1.2 documentation + Can I Debug Javet in Chrome DevTools? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/troubleshooting/index.html b/docs/faq/troubleshooting/index.html index 0d3d9165a..366526283 100644 --- a/docs/faq/troubleshooting/index.html +++ b/docs/faq/troubleshooting/index.html @@ -5,7 +5,7 @@ - Troubleshooting - Javet 2.1.2 documentation + Troubleshooting - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/faq/troubleshooting/why_node_js_crashes_when_being_closed.html b/docs/faq/troubleshooting/why_node_js_crashes_when_being_closed.html index b870227d7..1f2b0c72c 100644 --- a/docs/faq/troubleshooting/why_node_js_crashes_when_being_closed.html +++ b/docs/faq/troubleshooting/why_node_js_crashes_when_being_closed.html @@ -5,7 +5,7 @@ - Why Node.js Crashes When being Closed? - Javet 2.1.2 documentation + Why Node.js Crashes When being Closed? - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/genindex.html b/docs/genindex.html index 34455c582..6ed209f91 100644 --- a/docs/genindex.html +++ b/docs/genindex.html @@ -4,7 +4,7 @@ - Index - Javet 2.1.2 documentation + Index - Javet 2.2.0 documentation @@ -123,7 +123,7 @@
    @@ -149,7 +149,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -220,7 +220,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/index.html b/docs/index.html index 7ea5a18ed..aa04336c0 100644 --- a/docs/index.html +++ b/docs/index.html @@ -5,7 +5,7 @@ - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -124,7 +124,7 @@

    Gradle Kotlin DSL

    -
    implementation("com.caoccao.javet:javet:2.1.2") // Linux and Windows (x86_64)
    -implementation("com.caoccao.javet:javet-macos:2.1.2") // Mac OS (x86_64 and arm64)
    -implementation("com.caoccao.javet:javet-android:2.1.2") // Android (arm, arm64, x86 and x86_64)
    +
    implementation("com.caoccao.javet:javet:2.2.0") // Linux and Windows (x86_64)
    +implementation("com.caoccao.javet:javet-macos:2.2.0") // Mac OS (x86_64 and arm64)
    +implementation("com.caoccao.javet:javet-android:2.2.0") // Android (arm, arm64, x86 and x86_64)
     

    Gradle Groovy DSL

    -
    implementation 'com.caoccao.javet:javet:2.1.2' // Linux and Windows (x86_64)
    -implementation 'com.caoccao.javet:javet-macos:2.1.2' // Mac OS (x86_64 and arm64)
    -implementation 'com.caoccao.javet:javet-android:2.1.2' // Android (arm, arm64, x86 and x86_64)
    +
    implementation 'com.caoccao.javet:javet:2.2.0' // Linux and Windows (x86_64)
    +implementation 'com.caoccao.javet:javet-macos:2.2.0' // Mac OS (x86_64 and arm64)
    +implementation 'com.caoccao.javet:javet-android:2.2.0' // Android (arm, arm64, x86 and x86_64)
     
    @@ -397,7 +398,7 @@

    DocumentsRelease Notes
  • FAQ
  • diff --git a/docs/reference/converters/bridge_converter.html b/docs/reference/converters/bridge_converter.html index fd01db99d..671e181b2 100644 --- a/docs/reference/converters/bridge_converter.html +++ b/docs/reference/converters/bridge_converter.html @@ -5,7 +5,7 @@ - Bridge Converter - Javet 2.1.2 documentation + Bridge Converter - Javet 2.2.0 documentation @@ -124,7 +124,7 @@

    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/reference/converters/custom_converter.html b/docs/reference/converters/custom_converter.html index 8c3049c5d..b0427d8c0 100644 --- a/docs/reference/converters/custom_converter.html +++ b/docs/reference/converters/custom_converter.html @@ -5,7 +5,7 @@ - Custom Converter - Javet 2.1.2 documentation + Custom Converter - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/reference/converters/index.html b/docs/reference/converters/index.html index 9bc5f6a93..89025edf4 100644 --- a/docs/reference/converters/index.html +++ b/docs/reference/converters/index.html @@ -5,7 +5,7 @@ - Converters - Javet 2.1.2 documentation + Converters - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/reference/converters/object_converter.html b/docs/reference/converters/object_converter.html index 3ad447f43..f336b341a 100644 --- a/docs/reference/converters/object_converter.html +++ b/docs/reference/converters/object_converter.html @@ -5,7 +5,7 @@ - Object Converter - Javet 2.1.2 documentation + Object Converter - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/reference/converters/primitive_converter.html b/docs/reference/converters/primitive_converter.html index f227240ab..b3b200c81 100644 --- a/docs/reference/converters/primitive_converter.html +++ b/docs/reference/converters/primitive_converter.html @@ -5,7 +5,7 @@ - Primitive Converter - Javet 2.1.2 documentation + Primitive Converter - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/reference/converters/proxy_converter.html b/docs/reference/converters/proxy_converter.html index 7f7b1d28d..5341e63a3 100644 --- a/docs/reference/converters/proxy_converter.html +++ b/docs/reference/converters/proxy_converter.html @@ -5,7 +5,7 @@ - Proxy Converter - Javet 2.1.2 documentation + Proxy Converter - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/reference/index.html b/docs/reference/index.html index c61bb57df..cda65a66f 100644 --- a/docs/reference/index.html +++ b/docs/reference/index.html @@ -5,7 +5,7 @@ - Reference - Javet 2.1.2 documentation + Reference - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/reference/javadoc/allclasses-frame.html b/docs/reference/javadoc/allclasses-frame.html index f1c5b28a1..34f3e98d9 100644 --- a/docs/reference/javadoc/allclasses-frame.html +++ b/docs/reference/javadoc/allclasses-frame.html @@ -3,7 +3,7 @@ -All Classes (javet 2.1.2 API) +All Classes (javet 2.2.0 API) @@ -13,9 +13,11 @@

    All Classes

    • BaseJavetConsoleInterceptor
    • BaseJavetConverter
    • +
    • BaseJavetDirectProxyHandler
    • BaseJavetInterceptor
    • BaseJavetProxyHandler
    • BaseJavetProxySymbolConverter
    • +
    • BaseJavetReflectionProxyHandler
    • BaseJavetScriptingException
    • BaseNodeModule
    • BaseV8Executor
    • @@ -27,11 +29,22 @@

      All Classes

    • IJavaSupplier
    • IJavetAnonymous
    • IJavetBiConsumer
    • +
    • IJavetBiFunction
    • IJavetBiIndexedConsumer
    • IJavetCallbackReceiver
    • IJavetClosable
    • IJavetConverter
    • -
    • IJavetDynamicObjectFactory
    • +
    • IJavetDirectCallable
    • +
    • IJavetDirectCallable.DirectCall
    • +
    • IJavetDirectCallable.GetterAndNoThis
    • +
    • IJavetDirectCallable.GetterAndThis
    • +
    • IJavetDirectCallable.NoThisAndNoResult
    • +
    • IJavetDirectCallable.NoThisAndResult
    • +
    • IJavetDirectCallable.SetterAndNoThis
    • +
    • IJavetDirectCallable.SetterAndThis
    • +
    • IJavetDirectCallable.ThisAndNoResult
    • +
    • IJavetDirectCallable.ThisAndResult
    • +
    • IJavetDirectProxyHandler
    • IJavetEngine
    • IJavetEngineGuard
    • IJavetEnginePool
    • @@ -45,12 +58,15 @@

      All Classes

    • IJavetPromiseRejectCallback
    • IJavetProxyHandler
    • IJavetProxySymbolConverter
    • +
    • IJavetReflectionObjectFactory
    • IJavetResettable
    • IJavetSupplier
    • IJavetUniConsumer
    • +
    • IJavetUniFunction
    • IJavetUniIndexedConsumer
    • INodeModule
    • INodeNative
    • +
    • IV8Cacheable
    • IV8Cloneable
    • IV8Context
    • IV8Convertible
    • @@ -84,17 +100,14 @@

      All Classes

    • JavetBridgeConverter
    • JavetCallbackContext
    • JavetCallbackReceiver
    • +
    • JavetCallbackType
    • JavetCompilationException
    • JavetConverterConfig
    • JavetConverterException
    • JavetDateTimeUtils
    • JavetDefaultLogger
    • -
    • JavetDynamicProxyClassHandler
    • -
    • JavetDynamicProxyFactory
    • -
    • JavetDynamicProxyFunctionHandler
    • -
    • JavetDynamicProxyObjectHandler
    • -
    • JavetDynamicProxyV8ValueFunctionInvocationHandler
    • -
    • JavetDynamicProxyV8ValueObjectInvocationHandler
    • +
    • JavetDirectProxyFunctionHandler
    • +
    • JavetDirectProxyObjectHandler
    • JavetEngine
    • JavetEngineConfig
    • JavetEngineGuard
    • @@ -119,6 +132,12 @@

      All Classes

    • JavetProxyConverter
    • JavetProxySymbolIterableConverter
    • JavetProxySymbolToPrimitiveConverter
    • +
    • JavetReflectionProxyClassHandler
    • +
    • JavetReflectionProxyFactory
    • +
    • JavetReflectionProxyFunctionHandler
    • +
    • JavetReflectionProxyObjectHandler
    • +
    • JavetReflectionProxyV8ValueFunctionInvocationHandler
    • +
    • JavetReflectionProxyV8ValueObjectInvocationHandler
    • JavetReflectionUtils
    • JavetResourceUtils
    • JavetScriptingError
    • diff --git a/docs/reference/javadoc/allclasses-noframe.html b/docs/reference/javadoc/allclasses-noframe.html index 5308c0fc8..90d286eab 100644 --- a/docs/reference/javadoc/allclasses-noframe.html +++ b/docs/reference/javadoc/allclasses-noframe.html @@ -3,7 +3,7 @@ -All Classes (javet 2.1.2 API) +All Classes (javet 2.2.0 API) @@ -13,9 +13,11 @@

      All Classes

      • BaseJavetConsoleInterceptor
      • BaseJavetConverter
      • +
      • BaseJavetDirectProxyHandler
      • BaseJavetInterceptor
      • BaseJavetProxyHandler
      • BaseJavetProxySymbolConverter
      • +
      • BaseJavetReflectionProxyHandler
      • BaseJavetScriptingException
      • BaseNodeModule
      • BaseV8Executor
      • @@ -27,11 +29,22 @@

        All Classes

      • IJavaSupplier
      • IJavetAnonymous
      • IJavetBiConsumer
      • +
      • IJavetBiFunction
      • IJavetBiIndexedConsumer
      • IJavetCallbackReceiver
      • IJavetClosable
      • IJavetConverter
      • -
      • IJavetDynamicObjectFactory
      • +
      • IJavetDirectCallable
      • +
      • IJavetDirectCallable.DirectCall
      • +
      • IJavetDirectCallable.GetterAndNoThis
      • +
      • IJavetDirectCallable.GetterAndThis
      • +
      • IJavetDirectCallable.NoThisAndNoResult
      • +
      • IJavetDirectCallable.NoThisAndResult
      • +
      • IJavetDirectCallable.SetterAndNoThis
      • +
      • IJavetDirectCallable.SetterAndThis
      • +
      • IJavetDirectCallable.ThisAndNoResult
      • +
      • IJavetDirectCallable.ThisAndResult
      • +
      • IJavetDirectProxyHandler
      • IJavetEngine
      • IJavetEngineGuard
      • IJavetEnginePool
      • @@ -45,12 +58,15 @@

        All Classes

      • IJavetPromiseRejectCallback
      • IJavetProxyHandler
      • IJavetProxySymbolConverter
      • +
      • IJavetReflectionObjectFactory
      • IJavetResettable
      • IJavetSupplier
      • IJavetUniConsumer
      • +
      • IJavetUniFunction
      • IJavetUniIndexedConsumer
      • INodeModule
      • INodeNative
      • +
      • IV8Cacheable
      • IV8Cloneable
      • IV8Context
      • IV8Convertible
      • @@ -84,17 +100,14 @@

        All Classes

      • JavetBridgeConverter
      • JavetCallbackContext
      • JavetCallbackReceiver
      • +
      • JavetCallbackType
      • JavetCompilationException
      • JavetConverterConfig
      • JavetConverterException
      • JavetDateTimeUtils
      • JavetDefaultLogger
      • -
      • JavetDynamicProxyClassHandler
      • -
      • JavetDynamicProxyFactory
      • -
      • JavetDynamicProxyFunctionHandler
      • -
      • JavetDynamicProxyObjectHandler
      • -
      • JavetDynamicProxyV8ValueFunctionInvocationHandler
      • -
      • JavetDynamicProxyV8ValueObjectInvocationHandler
      • +
      • JavetDirectProxyFunctionHandler
      • +
      • JavetDirectProxyObjectHandler
      • JavetEngine
      • JavetEngineConfig
      • JavetEngineGuard
      • @@ -119,6 +132,12 @@

        All Classes

      • JavetProxyConverter
      • JavetProxySymbolIterableConverter
      • JavetProxySymbolToPrimitiveConverter
      • +
      • JavetReflectionProxyClassHandler
      • +
      • JavetReflectionProxyFactory
      • +
      • JavetReflectionProxyFunctionHandler
      • +
      • JavetReflectionProxyObjectHandler
      • +
      • JavetReflectionProxyV8ValueFunctionInvocationHandler
      • +
      • JavetReflectionProxyV8ValueObjectInvocationHandler
      • JavetReflectionUtils
      • JavetResourceUtils
      • JavetScriptingError
      • diff --git a/docs/reference/javadoc/com/caoccao/javet/annotations/CheckReturnValue.html b/docs/reference/javadoc/com/caoccao/javet/annotations/CheckReturnValue.html index 6c77643f6..f7d3a3462 100644 --- a/docs/reference/javadoc/com/caoccao/javet/annotations/CheckReturnValue.html +++ b/docs/reference/javadoc/com/caoccao/javet/annotations/CheckReturnValue.html @@ -3,7 +3,7 @@ -CheckReturnValue (javet 2.1.2 API) +CheckReturnValue (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/annotations/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/annotations/package-summary.html index 24161526a..d7a2cf2e8 100644 --- a/docs/reference/javadoc/com/caoccao/javet/annotations/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/annotations/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.annotations (javet 2.1.2 API) +com.caoccao.javet.annotations (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/entities/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/entities/package-summary.html index 6eb77487f..40cd47d98 100644 --- a/docs/reference/javadoc/com/caoccao/javet/entities/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/entities/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.entities (javet 2.1.2 API) +com.caoccao.javet.entities (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/enums/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/enums/package-summary.html index 3e68d3e9d..188bdda97 100644 --- a/docs/reference/javadoc/com/caoccao/javet/enums/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/enums/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.enums (javet 2.1.2 API) +com.caoccao.javet.enums (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/exceptions/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/exceptions/package-summary.html index 2c263fa9f..17e092172 100644 --- a/docs/reference/javadoc/com/caoccao/javet/exceptions/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/exceptions/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.exceptions (javet 2.1.2 API) +com.caoccao.javet.exceptions (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interception/logging/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interception/logging/package-summary.html index 70782ea07..acb538105 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interception/logging/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interception/logging/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interception.logging (javet 2.1.2 API) +com.caoccao.javet.interception.logging (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interception/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interception/package-summary.html index 6d2e77715..b70cc2e87 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interception/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interception/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interception (javet 2.1.2 API) +com.caoccao.javet.interception (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ + + + + + + + + + +
        +
        com.caoccao.javet.interfaces
        +

        Interface IJavetBiFunction<T1,T2,R,E extends java.lang.Throwable>

        +
        +
        +
        +
          +
        • +
          +
          Type Parameters:
          +
          T1 - the type parameter
          +
          T2 - the type parameter
          +
          R - the type parameter
          +
          E - the type parameter
          +
          +
          +
          Functional Interface:
          +
          This is a functional interface and can therefore be used as the assignment target for a lambda expression or method reference.
          +
          +
          +
          +
          @FunctionalInterface
          +public interface IJavetBiFunction<T1,T2,R,E extends java.lang.Throwable>
          +
          The interface Javet bi-function.
          +
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        +
        +
        + +
        +
        +
          +
        • + +
            +
          • + + +

            Method Detail

            + + + + + +
              +
            • +

              apply

              +
              R apply(T1 value1,
              +        T2 value2)
              + throws JavetException,
              +        E extends java.lang.Throwable
              +
              Apply.
              +
              +
              Parameters:
              +
              value1 - the value 1
              +
              value2 - the value 2
              +
              Returns:
              +
              the result
              +
              Throws:
              +
              JavetException - the javet exception
              +
              E - the custom exception
              +
              E extends java.lang.Throwable
              +
              Since:
              +
              2.2.0
              +
              +
            • +
            +
          • +
          +
        • +
        +
        +
        + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetBiIndexedConsumer.html b/docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetBiIndexedConsumer.html index 83ed476ff..7299d38fe 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetBiIndexedConsumer.html +++ b/docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetBiIndexedConsumer.html @@ -3,7 +3,7 @@ -IJavetBiIndexedConsumer (javet 2.1.2 API) +IJavetBiIndexedConsumer (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ + + + + + + + + + +
        +
        com.caoccao.javet.interfaces
        +

        Interface IJavetUniFunction<T,R,E extends java.lang.Throwable>

        +
        +
        +
        +
          +
        • +
          +
          Type Parameters:
          +
          T - the type parameter
          +
          R - the type parameter
          +
          E - the type parameter
          +
          +
          +
          Functional Interface:
          +
          This is a functional interface and can therefore be used as the assignment target for a lambda expression or method reference.
          +
          +
          +
          +
          @FunctionalInterface
          +public interface IJavetUniFunction<T,R,E extends java.lang.Throwable>
          +
          The interface Javet uni-function.
          +
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        +
        +
        + +
        +
        +
          +
        • + +
            +
          • + + +

            Method Detail

            + + + + + +
              +
            • +

              apply

              +
              R apply(T value)
              + throws JavetException,
              +        E extends java.lang.Throwable
              +
              Apply.
              +
              +
              Parameters:
              +
              value - the value
              +
              Returns:
              +
              the result
              +
              Throws:
              +
              JavetException - the javet exception
              +
              E - the custom exception
              +
              E extends java.lang.Throwable
              +
              Since:
              +
              2.2.0
              +
              +
            • +
            +
          • +
          +
        • +
        +
        +
        + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetUniIndexedConsumer.html b/docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetUniIndexedConsumer.html index 71581794f..144d6aa1e 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetUniIndexedConsumer.html +++ b/docs/reference/javadoc/com/caoccao/javet/interfaces/IJavetUniIndexedConsumer.html @@ -3,7 +3,7 @@ -IJavetUniIndexedConsumer (javet 2.1.2 API) +IJavetUniIndexedConsumer (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -17,6 +17,7 @@

        Interfaces

      • IJavaSupplier
      • IJavetAnonymous
      • IJavetBiConsumer
      • +
      • IJavetBiFunction
      • IJavetBiIndexedConsumer
      • IJavetClosable
      • IJavetEntityFunction
      • @@ -27,6 +28,7 @@

        Interfaces

      • IJavetResettable
      • IJavetSupplier
      • IJavetUniConsumer
      • +
      • IJavetUniFunction
      • IJavetUniIndexedConsumer
      • IV8ModuleResolver
      diff --git a/docs/reference/javadoc/com/caoccao/javet/interfaces/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interfaces/package-summary.html index 571d0c92d..0593bc0c7 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interfaces/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interfaces/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interfaces (javet 2.1.2 API) +com.caoccao.javet.interfaces (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/binding/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/binding/package-summary.html index e92c6ebae..c094c9a7b 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/binding/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/binding/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.binding (javet 2.1.2 API) +com.caoccao.javet.interop.binding (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable.DirectCall

      +
      +
      +
      + +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.GetterAndNoThis.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.GetterAndNoThis.html new file mode 100644 index 000000000..4f5370023 --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.GetterAndNoThis.html @@ -0,0 +1,250 @@ + + + + + +IJavetDirectCallable.GetterAndNoThis (javet 2.2.0 API) + + + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable.GetterAndNoThis<E extends java.lang.Exception>

      +
      +
      +
      + +
      +
      +
        +
      • + + +
      • +
      +
      +
      +
        +
      • + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            get

            +
            V8Value get()
            +     throws JavetException,
            +            E extends java.lang.Exception
            +
            Get the property value by a property key + without this object passed in.
            +
            +
            Returns:
            +
            the V8 value
            +
            Throws:
            +
            JavetException - the javet exception
            +
            E - the custom exception
            +
            E extends java.lang.Exception
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.GetterAndThis.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.GetterAndThis.html new file mode 100644 index 000000000..6046054cc --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.GetterAndThis.html @@ -0,0 +1,252 @@ + + + + + +IJavetDirectCallable.GetterAndThis (javet 2.2.0 API) + + + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable.GetterAndThis<E extends java.lang.Exception>

      +
      +
      +
      + +
      +
      + +
      +
      +
        +
      • + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            get

            +
            V8Value get(V8Value thisObject)
            +     throws JavetException,
            +            E extends java.lang.Exception
            +
            Get the property value by a property key + with this object passed in.
            +
            +
            Parameters:
            +
            thisObject - the this object
            +
            Returns:
            +
            the V8 value
            +
            Throws:
            +
            JavetException - the javet exception
            +
            E - the custom exception
            +
            E extends java.lang.Exception
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.NoThisAndNoResult.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.NoThisAndNoResult.html new file mode 100644 index 000000000..987cb5311 --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.NoThisAndNoResult.html @@ -0,0 +1,247 @@ + + + + + +IJavetDirectCallable.NoThisAndNoResult (javet 2.2.0 API) + + + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable.NoThisAndNoResult<E extends java.lang.Exception>

      +
      +
      +
      + +
      +
      + +
      +
      +
        +
      • + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            call

            +
            void call(V8Value... v8Values)
            +   throws JavetException,
            +          E extends java.lang.Exception
            +
            Call.
            +
            +
            Parameters:
            +
            v8Values - the V8 values
            +
            Throws:
            +
            JavetException - the javet exception
            +
            E - the custom exception
            +
            E extends java.lang.Exception
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.NoThisAndResult.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.NoThisAndResult.html new file mode 100644 index 000000000..b19af9b31 --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.NoThisAndResult.html @@ -0,0 +1,250 @@ + + + + + +IJavetDirectCallable.NoThisAndResult (javet 2.2.0 API) + + + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable.NoThisAndResult<E extends java.lang.Exception>

      +
      +
      +
      + +
      +
      + +
      +
      +
        +
      • + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            call

            +
            V8Value call(V8Value... v8Values)
            +      throws JavetException,
            +             E extends java.lang.Exception
            +
            Call and return the result.
            +
            +
            Parameters:
            +
            v8Values - the V8 values
            +
            Returns:
            +
            the V8 value
            +
            Throws:
            +
            JavetException - the javet exception
            +
            E - the custom exception
            +
            E extends java.lang.Exception
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.SetterAndNoThis.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.SetterAndNoThis.html new file mode 100644 index 000000000..13ff3024a --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.SetterAndNoThis.html @@ -0,0 +1,252 @@ + + + + + +IJavetDirectCallable.SetterAndNoThis (javet 2.2.0 API) + + + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable.SetterAndNoThis<E extends java.lang.Exception>

      +
      +
      +
      + +
      +
      + +
      +
      +
        +
      • + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            set

            +
            V8Value set(V8Value v8ValueValue)
            +     throws JavetException,
            +            E extends java.lang.Exception
            +
            Set the property value by a property key + without this object passed in.
            +
            +
            Parameters:
            +
            v8ValueValue - the V8 value value
            +
            Returns:
            +
            the V8 value
            +
            Throws:
            +
            JavetException - the javet exception
            +
            E - the custom exception
            +
            E extends java.lang.Exception
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.SetterAndThis.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.SetterAndThis.html new file mode 100644 index 000000000..f1f786e82 --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.SetterAndThis.html @@ -0,0 +1,255 @@ + + + + + +IJavetDirectCallable.SetterAndThis (javet 2.2.0 API) + + + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable.SetterAndThis<E extends java.lang.Exception>

      +
      +
      +
      + +
      +
      + +
      +
      +
        +
      • + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            set

            +
            V8Value set(V8Value thisObject,
            +            V8Value v8ValueValue)
            +     throws JavetException,
            +            E extends java.lang.Exception
            +
            Set the property value by a property key + with this object passed in.
            +
            +
            Parameters:
            +
            thisObject - the this object
            +
            v8ValueValue - the V8 value value
            +
            Returns:
            +
            the V8 value
            +
            Throws:
            +
            JavetException - the javet exception
            +
            E - the custom exception
            +
            E extends java.lang.Exception
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.ThisAndNoResult.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.ThisAndNoResult.html new file mode 100644 index 000000000..099f3db76 --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.ThisAndNoResult.html @@ -0,0 +1,250 @@ + + + + + +IJavetDirectCallable.ThisAndNoResult (javet 2.2.0 API) + + + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable.ThisAndNoResult<E extends java.lang.Exception>

      +
      +
      +
      + +
      +
      + +
      +
      +
        +
      • + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            call

            +
            void call(V8Value thisObject,
            +          V8Value... v8Values)
            +   throws JavetException,
            +          E extends java.lang.Exception
            +
            Call by this object.
            +
            +
            Parameters:
            +
            thisObject - the this object
            +
            v8Values - the V8 values
            +
            Throws:
            +
            JavetException - the javet exception
            +
            E - the custom exception
            +
            E extends java.lang.Exception
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.ThisAndResult.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.ThisAndResult.html new file mode 100644 index 000000000..7889e4488 --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.ThisAndResult.html @@ -0,0 +1,256 @@ + + + + + +IJavetDirectCallable.ThisAndResult (javet 2.2.0 API) + + + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable.ThisAndResult<E extends java.lang.Exception>

      +
      +
      +
      +
        +
      • +
        +
        Type Parameters:
        +
        E - the custom exception
        +
        +
        +
        All Superinterfaces:
        +
        IJavetDirectCallable.DirectCall, java.io.Serializable
        +
        +
        +
        Enclosing interface:
        +
        IJavetDirectCallable
        +
        +
        +
        +
        public static interface IJavetDirectCallable.ThisAndResult<E extends java.lang.Exception>
        +extends IJavetDirectCallable.DirectCall
        +
        The interface ThisAndResult accepts this object and returns the result.
        +
        +
        Since:
        +
        2.2.0
        +
        +
      • +
      +
      +
      + +
      +
      +
        +
      • + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            call

            +
            V8Value call(V8Value thisObject,
            +             V8Value... v8Values)
            +      throws JavetException,
            +             E extends java.lang.Exception
            +
            Call by this object and return the result.
            +
            +
            Parameters:
            +
            thisObject - the this object
            +
            v8Values - the V8 values
            +
            Returns:
            +
            the V8 value
            +
            Throws:
            +
            JavetException - the javet exception
            +
            E - the custom exception
            +
            E extends java.lang.Exception
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.html new file mode 100644 index 000000000..acabc2045 --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetDirectCallable.html @@ -0,0 +1,333 @@ + + + + + +IJavetDirectCallable (javet 2.2.0 API) + + + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Interface IJavetDirectCallable

      +
      +
      +
      + +
      +
      + +
      +
      +
        +
      • + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            getCallbackContexts

            +
            JavetCallbackContext[] getCallbackContexts()
            +
            Get supported callback contexts.
            +
            +
            Returns:
            +
            the supported callback contexts
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            setV8Runtime

            +
            default void setV8Runtime(V8Runtime v8Runtime)
            +
            Sets V8 runtime.
            +
            +
            Parameters:
            +
            v8Runtime - the V8 runtime
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetGCCallback.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetGCCallback.html index d3d4314df..186b2dc27 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetGCCallback.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/IJavetGCCallback.html @@ -3,7 +3,7 @@ -IJavetGCCallback (javet 2.1.2 API) +IJavetGCCallback (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ + + + + + + + + + +
      +
      com.caoccao.javet.interop.callback
      +

      Enum JavetCallbackType

      +
      +
      +
        +
      • java.lang.Object
      • +
      • +
          +
        • java.lang.Enum<JavetCallbackType>
        • +
        • +
            +
          • com.caoccao.javet.interop.callback.JavetCallbackType
          • +
          +
        • +
        +
      • +
      +
      +
        +
      • +
        +
        All Implemented Interfaces:
        +
        java.io.Serializable, java.lang.Comparable<JavetCallbackType>
        +
        +
        +
        +
        public enum JavetCallbackType
        +extends java.lang.Enum<JavetCallbackType>
        +
        The enum Javet callback type.
        +
        +
        Since:
        +
        2.2.0
        +
        +
      • +
      +
      +
      + +
      +
      +
        +
      • + +
          +
        • + + +

          Enum Constant Detail

          + + + +
            +
          • +

            DirectCallGetterAndNoThis

            +
            public static final JavetCallbackType DirectCallGetterAndNoThis
            +
            The callback is via Java direct getter without this object.
            +
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            DirectCallGetterAndThis

            +
            public static final JavetCallbackType DirectCallGetterAndThis
            +
            The callback is via Java direct getter with this object.
            +
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            DirectCallSetterAndNoThis

            +
            public static final JavetCallbackType DirectCallSetterAndNoThis
            +
            The callback is via Java direct setter without this object.
            +
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            DirectCallSetterAndThis

            +
            public static final JavetCallbackType DirectCallSetterAndThis
            +
            The callback is via Java direct setter with this object.
            +
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            DirectCallNoThisAndNoResult

            +
            public static final JavetCallbackType DirectCallNoThisAndNoResult
            +
            The callback is via Java direct call without this object and without result.
            +
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            DirectCallNoThisAndResult

            +
            public static final JavetCallbackType DirectCallNoThisAndResult
            +
            The callback is via Java direct call without this object and with result.
            +
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            DirectCallThisAndNoResult

            +
            public static final JavetCallbackType DirectCallThisAndNoResult
            +
            The callback is via Java direct call with this object and without result.
            +
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            DirectCallThisAndResult

            +
            public static final JavetCallbackType DirectCallThisAndResult
            +
            The callback is via Java direct call with this object and with result.
            +
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            Reflection

            +
            public static final JavetCallbackType Reflection
            +
            The callback is via Java reflection. +

            + PROS: It's non-intrusive and supports all kinds of Java classes. + CONS: Performance is relatively low.

            +
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        + +
          +
        • + + +

          Method Detail

          + + + +
            +
          • +

            values

            +
            public static JavetCallbackType[] values()
            +
            Returns an array containing the constants of this enum type, in +the order they are declared. This method may be used to iterate +over the constants as follows: +
            +for (JavetCallbackType c : JavetCallbackType.values())
            +    System.out.println(c);
            +
            +
            +
            Returns:
            +
            an array containing the constants of this enum type, in the order they are declared
            +
            +
          • +
          + + + +
            +
          • +

            valueOf

            +
            public static JavetCallbackType valueOf(java.lang.String name)
            +
            Returns the enum constant of this type with the specified name. +The string must match exactly an identifier used to declare an +enum constant in this type. (Extraneous whitespace characters are +not permitted.)
            +
            +
            Parameters:
            +
            name - the name of the enum constant to be returned.
            +
            Returns:
            +
            the enum constant with the specified name
            +
            Throws:
            +
            java.lang.IllegalArgumentException - if this enum type has no constant with the specified name
            +
            java.lang.NullPointerException - if the argument is null
            +
            +
          • +
          + + + +
            +
          • +

            getDirectCallClass

            +
            public java.lang.Class<? extends IJavetDirectCallable.DirectCall> getDirectCallClass()
            +
            Gets direct call class.
            +
            +
            Returns:
            +
            the direct call class
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            getReturnResult

            +
            public java.lang.Boolean getReturnResult()
            +
            Gets return result.
            +
            +
            Returns:
            +
            the return result
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          + + + +
            +
          • +

            getThisObjectRequired

            +
            public java.lang.Boolean getThisObjectRequired()
            +
            Gets this object required.
            +
            +
            Returns:
            +
            the this object required
            +
            Since:
            +
            2.2.0
            +
            +
          • +
          +
        • +
        +
      • +
      +
      +
      + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/JavetGCCallback.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/JavetGCCallback.html index d11f9c0e7..1e7545ee5 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/callback/JavetGCCallback.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/JavetGCCallback.html @@ -3,7 +3,7 @@ -JavetGCCallback (javet 2.1.2 API) +JavetGCCallback (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -12,6 +12,16 @@

      Interfaces

      @@ -22,6 +32,10 @@

      Classes

    • JavetPromiseRejectCallback
    • V8FunctionCallback
    +

    Enums

    +
    diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/callback/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/callback/package-summary.html index 016d7886b..d3512bad6 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/callback/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/callback/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.callback (javet 2.1.2 API) +com.caoccao.javet.interop.callback (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/converters/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/converters/package-summary.html index 442b50b17..9827e70c5 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/converters/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/converters/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.converters (javet 2.1.2 API) +com.caoccao.javet.interop.converters (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/engine/observers/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/engine/observers/package-summary.html index 55eec9570..cdddbddc9 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/engine/observers/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/engine/observers/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.engine.observers (javet 2.1.2 API) +com.caoccao.javet.interop.engine.observers (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/engine/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/engine/package-summary.html index e4a623105..aefd45036 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/engine/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/engine/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.engine (javet 2.1.2 API) +com.caoccao.javet.interop.engine (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/executors/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/executors/package-summary.html index 394fd3886..67b8340d3 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/executors/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/executors/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.executors (javet 2.1.2 API) +com.caoccao.javet.interop.executors (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/loader/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/loader/package-summary.html index 00cc328e6..543a9fe5b 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/loader/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/loader/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.loader (javet 2.1.2 API) +com.caoccao.javet.interop.loader (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/monitoring/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/monitoring/package-summary.html index b3130850e..6943cd7fc 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/monitoring/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/monitoring/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.monitoring (javet 2.1.2 API) +com.caoccao.javet.interop.monitoring (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/options/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/options/package-summary.html index a05cddb77..c4a39b3ae 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/options/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/options/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.options (javet 2.1.2 API) +com.caoccao.javet.interop.options (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/package-summary.html index ec81d30da..c2153f94f 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop (javet 2.1.2 API) +com.caoccao.javet.interop (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ + + + + + + + + + +
    +
    com.caoccao.javet.interop.proxy
    +

    Class BaseJavetDirectProxyHandler<T extends IJavetDirectProxyHandler<E>,E extends java.lang.Exception>

    +
    +
    + +
    + +
    +
    + +
    +
    +
      +
    • + +
        +
      • + + +

        Constructor Detail

        + + + + + +
          +
        • +

          BaseJavetDirectProxyHandler

          +
          public BaseJavetDirectProxyHandler(V8Runtime v8Runtime,
          +                                   T targetObject)
          +
          Instantiates a new Base javet direct proxy handler.
          +
          +
          Parameters:
          +
          v8Runtime - the V8 runtime
          +
          targetObject - the target object
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        +
      • +
      +
    • +
    +
    +
    + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/BaseJavetProxyHandler.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/BaseJavetProxyHandler.html index b3afa441c..8e3e47f77 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/BaseJavetProxyHandler.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/BaseJavetProxyHandler.html @@ -3,7 +3,7 @@ -BaseJavetProxyHandler (javet 2.1.2 API) +BaseJavetProxyHandler (javet 2.2.0 API) @@ -11,14 +11,14 @@ @@ -11,7 +11,7 @@ + + + + + + + + + +
    +
    com.caoccao.javet.interop.proxy
    +

    Class BaseJavetReflectionProxyHandler<T,E extends java.lang.Exception>

    +
    +
    + +
    + +
    +
    + +
    +
    +
      +
    • + +
        +
      • + + +

        Field Detail

        + + + +
          +
        • +

          GETTER_PREFIX_ARRAY

          +
          protected static final java.lang.String[] GETTER_PREFIX_ARRAY
          +
          The constant GETTER_PREFIX_ARRAY.
          +
          +
          Since:
          +
          0.9.6
          +
          +
        • +
        + + + +
          +
        • +

          PATTERN_CAPITALIZED_PREFIX

          +
          protected static final java.util.regex.Pattern PATTERN_CAPITALIZED_PREFIX
          +
          The constant PATTERN_CAPITALIZED_PREFIX.
          +
          +
          Since:
          +
          0.9.7
          +
          +
        • +
        + + + +
          +
        • +

          SETTER_PREFIX_ARRAY

          +
          protected static final java.lang.String[] SETTER_PREFIX_ARRAY
          +
          The constant SETTER_PREFIX_ARRAY.
          +
          +
          Since:
          +
          0.9.6
          +
          +
        • +
        + + + +
          +
        • +

          classDescriptor

          +
          protected ClassDescriptor classDescriptor
          +
          The Class descriptor.
          +
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          reflectionObjectFactory

          +
          protected IJavetReflectionObjectFactory reflectionObjectFactory
          +
          The Reflection object factory.
          +
          +
          Since:
          +
          2.0.1
          +
          +
        • +
        +
      • +
      + +
        +
      • + + +

        Constructor Detail

        + + + + + +
          +
        • +

          BaseJavetReflectionProxyHandler

          +
          public BaseJavetReflectionProxyHandler(V8Runtime v8Runtime,
          +                                       IJavetReflectionObjectFactory reflectionObjectFactory,
          +                                       T targetObject)
          +
          Instantiates a new Base javet reflection proxy handler.
          +
          +
          Parameters:
          +
          v8Runtime - the V8 runtime
          +
          reflectionObjectFactory - the reflection object factory
          +
          targetObject - the target object
          +
          Since:
          +
          0.9.6
          +
          +
        • +
        +
      • +
      + +
        +
      • + + +

        Method Detail

        + + + +
          +
        • +

          execute

          +
          protected static <E extends java.lang.reflect.AccessibleObject> java.lang.Object execute(IJavetReflectionObjectFactory reflectionObjectFactory,
          +                                                                                         java.lang.Object targetObject,
          +                                                                                         V8ValueObject thisObject,
          +                                                                                         java.util.List<E> executables,
          +                                                                                         JavetVirtualObject[] javetVirtualObjects)
          +                                                                                  throws java.lang.Throwable
          +
          Execute.
          +
          +
          Type Parameters:
          +
          E - the type parameter
          +
          Parameters:
          +
          reflectionObjectFactory - the reflection object factory
          +
          targetObject - the target object
          +
          thisObject - this object
          +
          executables - the executables
          +
          javetVirtualObjects - the javet virtual objects
          +
          Returns:
          +
          the object
          +
          Throws:
          +
          java.lang.Throwable - the throwable
          +
          Since:
          +
          0.9.10
          +
          +
        • +
        + + + +
          +
        • +

          addMethod

          +
          protected void addMethod(java.lang.reflect.Method method,
          +                         int startIndex,
          +                         java.util.Map<java.lang.String,java.util.List<java.lang.reflect.Method>> map)
          +
          Add method.
          +
          +
          Parameters:
          +
          method - the method
          +
          startIndex - the start index
          +
          map - the map
          +
          Since:
          +
          0.9.6
          +
          +
        • +
        + + + +
          +
        • +

          getClassDescriptorCache

          +
          public abstract ThreadSafeMap<java.lang.Class<?>,ClassDescriptor> getClassDescriptorCache()
          +
          Gets class descriptor cache.
          +
          +
          Returns:
          +
          the thread safe map
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          getFromField

          +
          protected V8Value getFromField(V8Value property)
          +                        throws JavetException
          +
          Gets from field.
          +
          +
          Parameters:
          +
          property - the property
          +
          Returns:
          +
          the V8 value
          +
          Throws:
          +
          JavetException - the javet exception
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          getFromGetter

          +
          protected V8Value getFromGetter(V8Value property)
          +                         throws JavetException
          +
          Gets from getter.
          +
          +
          Parameters:
          +
          property - the property
          +
          Returns:
          +
          the V8 value
          +
          Throws:
          +
          JavetException - the javet exception
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          getFromMethod

          +
          protected V8Value getFromMethod(V8Value target,
          +                                V8Value property)
          +                         throws JavetException
          +
          Gets from method.
          +
          +
          Parameters:
          +
          target - the target
          +
          property - the property
          +
          Returns:
          +
          the V8 value
          +
          Throws:
          +
          JavetException - the javet exception
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          getGetterPrefixLength

          +
          protected int getGetterPrefixLength(java.lang.reflect.Method method)
          +
          Gets getter prefix length.
          +
          +
          Parameters:
          +
          method - the method
          +
          Returns:
          +
          the getter prefix length
          +
          Since:
          +
          0.9.6
          +
          +
        • +
        + + + +
          +
        • +

          getSetterPrefixLength

          +
          protected int getSetterPrefixLength(java.lang.reflect.Method method)
          +
          Gets setter prefix length.
          +
          +
          Parameters:
          +
          method - the method
          +
          Returns:
          +
          the setter prefix length
          +
          Since:
          +
          0.9.6
          +
          +
        • +
        + + + +
          +
        • +

          hasFromGeneric

          +
          protected boolean hasFromGeneric(V8Value property)
          +                          throws JavetException
          +
          Has from generic.
          +
          +
          Parameters:
          +
          property - the property
          +
          Returns:
          +
          the boolean
          +
          Throws:
          +
          JavetException - the javet exception
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          hasFromRegular

          +
          protected boolean hasFromRegular(V8Value property)
          +
          Has from regular.
          +
          +
          Parameters:
          +
          property - the property
          +
          Returns:
          +
          true : has, false: not has
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          initialize

          +
          protected abstract void initialize()
          +
          Initialize.
          +
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          initializeConstructors

          +
          protected void initializeConstructors(java.lang.Class<?> currentClass,
          +                                      V8ConversionMode conversionMode)
          +
          Initialize constructors.
          +
          +
          Parameters:
          +
          currentClass - the current class
          +
          conversionMode - the conversion mode
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          initializePublicFields

          +
          protected void initializePublicFields(java.lang.Class<?> currentClass,
          +                                      V8ConversionMode conversionMode,
          +                                      boolean staticMode)
          +
          Initialize public fields.
          +
          +
          Parameters:
          +
          currentClass - the current class
          +
          conversionMode - the conversion mode
          +
          staticMode - the static mode
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          initializePublicMethods

          +
          protected void initializePublicMethods(java.lang.Class<?> currentClass,
          +                                       V8ConversionMode conversionMode,
          +                                       boolean staticMode)
          +
          Initialize public methods.
          +
          +
          Parameters:
          +
          currentClass - the current class
          +
          conversionMode - the conversion mode
          +
          staticMode - the static mode
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          isAllowed

          +
          protected boolean isAllowed(V8ConversionMode conversionMode,
          +                            java.lang.reflect.AccessibleObject accessibleObject)
          +
          Is allowed.
          +
          +
          Parameters:
          +
          conversionMode - the conversion mode
          +
          accessibleObject - the accessible object
          +
          Returns:
          +
          true : allowed, false : disallowed
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          isApplyFunction

          +
          protected boolean isApplyFunction(java.lang.reflect.Method method)
          +
          Is apply function.
          +
          +
          Parameters:
          +
          method - the method
          +
          Returns:
          +
          true : yes, false: no
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          isGenericGetter

          +
          protected boolean isGenericGetter(java.lang.reflect.Method method)
          +
          Is generic getter.
          +
          +
          Parameters:
          +
          method - the method
          +
          Returns:
          +
          true : yes, false : no
          +
          Since:
          +
          0.9.6
          +
          +
        • +
        + + + +
          +
        • +

          isGenericSetter

          +
          protected boolean isGenericSetter(java.lang.reflect.Method method)
          +
          Is generic setter.
          +
          +
          Parameters:
          +
          method - the method
          +
          Returns:
          +
          true : yes, false : no
          +
          Since:
          +
          0.9.6
          +
          +
        • +
        + + + +
          +
        • +

          setToField

          +
          protected boolean setToField(V8Value propertyKey,
          +                             V8Value propertyValue)
          +                      throws JavetException
          +
          Sets to field.
          +
          +
          Parameters:
          +
          propertyKey - the property key
          +
          propertyValue - the property value
          +
          Returns:
          +
          true : set, false: not set
          +
          Throws:
          +
          JavetException - the javet exception
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        + + + +
          +
        • +

          setToSetter

          +
          protected boolean setToSetter(V8Value target,
          +                              V8Value propertyKey,
          +                              V8Value propertyValue)
          +                       throws JavetException
          +
          Sets to setter.
          +
          +
          Parameters:
          +
          target - the target
          +
          propertyKey - the property key
          +
          propertyValue - the property value
          +
          Returns:
          +
          true : set, false: not set
          +
          Throws:
          +
          JavetException - the javet exception
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        +
      • +
      +
    • +
    +
    +
    + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/IJavetDirectProxyHandler.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/IJavetDirectProxyHandler.html new file mode 100644 index 000000000..44749fc73 --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/IJavetDirectProxyHandler.html @@ -0,0 +1,580 @@ + + + + + +IJavetDirectProxyHandler (javet 2.2.0 API) + + + + + + + + + + + +
    +
    com.caoccao.javet.interop.proxy
    +

    Interface IJavetDirectProxyHandler<E extends java.lang.Exception>

    +
    +
    +
    +
      +
    • +
      +
      Type Parameters:
      +
      E - the type parameter
      +
      +
      +
      +
      public interface IJavetDirectProxyHandler<E extends java.lang.Exception>
      +
      The interface Javet direct proxy handler.
      +
      +
      Since:
      +
      2.2.0
      +
      +
    • +
    +
    +
    + +
    +
    +
      +
    • + +
        +
      • + + +

        Method Detail

        + + + +
          +
        • +

          getV8Runtime

          +
          V8Runtime getV8Runtime()
          +
          Gets V8 runtime.
          +
          +
          Returns:
          +
          the V8 runtime
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          proxyApply

          +
          default V8Value proxyApply(V8Value target,
          +                           V8Value thisObject,
          +                           V8ValueArray arguments)
          +                    throws JavetException,
          +                           E extends java.lang.Exception
          +
          Apply to object.
          +
          +
          Parameters:
          +
          target - the target
          +
          thisObject - this object
          +
          arguments - the arguments
          +
          Returns:
          +
          the V8 value
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          proxyGet

          +
          default V8Value proxyGet(V8Value target,
          +                         V8Value property,
          +                         V8Value receiver)
          +                  throws JavetException,
          +                         E extends java.lang.Exception
          +
          Get by property.
          +
          +
          Parameters:
          +
          target - the target
          +
          property - the property
          +
          receiver - the receiver
          +
          Returns:
          +
          the V8 value
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          proxyGetStringGetterMap

          +
          default java.util.Map<java.lang.String,IJavetUniFunction<java.lang.String,? extends V8Value,E>> proxyGetStringGetterMap()
          +
          Proxy get string getter map.
          +
          +
          Returns:
          +
          the map
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          proxyGetStringSetterMap

          +
          default java.util.Map<java.lang.String,IJavetBiFunction<java.lang.String,V8Value,java.lang.Boolean,E>> proxyGetStringSetterMap()
          +
          Proxy get string setter map.
          +
          +
          Returns:
          +
          the map
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          proxyGetSymbolGetterMap

          +
          default java.util.Map<java.lang.String,IJavetUniFunction<V8ValueSymbol,? extends V8Value,E>> proxyGetSymbolGetterMap()
          +
          Proxy get symbol getter map.
          +
          +
          Returns:
          +
          the map
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          proxyGetSymbolSetterMap

          +
          default java.util.Map<java.lang.String,IJavetBiFunction<V8ValueSymbol,V8Value,java.lang.Boolean,E>> proxyGetSymbolSetterMap()
          +
          Proxy get symbol setter map.
          +
          +
          Returns:
          +
          the map
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          proxyHas

          +
          default V8ValueBoolean proxyHas(V8Value target,
          +                                V8Value property)
          +                         throws JavetException,
          +                                E extends java.lang.Exception
          +
          Has property
          +
          +
          Parameters:
          +
          target - the target
          +
          property - the property
          +
          Returns:
          +
          the V8 value boolean
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          proxyOwnKeys

          +
          default V8ValueArray proxyOwnKeys(V8Value target)
          +                           throws JavetException,
          +                                  E extends java.lang.Exception
          +
          Own keys.
          +
          +
          Parameters:
          +
          target - the target
          +
          Returns:
          +
          the V8 value array
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          proxySet

          +
          default V8ValueBoolean proxySet(V8Value target,
          +                                V8Value propertyKey,
          +                                V8Value propertyValue,
          +                                V8Value receiver)
          +                         throws JavetException,
          +                                E extends java.lang.Exception
          +
          Set value by property.
          +
          +
          Parameters:
          +
          target - the target
          +
          propertyKey - the property key
          +
          propertyValue - the property value
          +
          receiver - the receiver
          +
          Returns:
          +
          the V8 value boolean
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          setV8Runtime

          +
          default void setV8Runtime(V8Runtime v8Runtime)
          +
          Sets V8 runtime.
          +
          +
          Parameters:
          +
          v8Runtime - the V8 runtime
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          symbolIterator

          +
          default V8Value symbolIterator(V8Value... v8Values)
          +                        throws JavetException,
          +                               E extends java.lang.Exception
          +
          Symbol iterator.
          +
          +
          Parameters:
          +
          v8Values - the V8 values
          +
          Returns:
          +
          the V8 value
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        + + + +
          +
        • +

          symbolToPrimitive

          +
          default V8Value symbolToPrimitive(V8Value... v8Values)
          +                           throws JavetException,
          +                                  E extends java.lang.Exception
          +
          Symbol toPrimitive.
          +
          +
          Parameters:
          +
          v8Values - the V8 values
          +
          Returns:
          +
          the V8 value
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        +
      • +
      +
    • +
    +
    +
    + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/IJavetProxyHandler.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/IJavetProxyHandler.html index aebbd1ca8..7777d01d2 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/IJavetProxyHandler.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/IJavetProxyHandler.html @@ -3,7 +3,7 @@ -IJavetProxyHandler (javet 2.1.2 API) +IJavetProxyHandler (javet 2.2.0 API) @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ + + + + + + + + + +
    +
    com.caoccao.javet.interop.proxy
    +

    Class JavetDirectProxyFunctionHandler<T extends IJavetDirectProxyHandler<E>,E extends java.lang.Exception>

    +
    +
    + +
    + +
    +
    + +
    +
    + +
    +
    + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDirectProxyObjectHandler.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDirectProxyObjectHandler.html new file mode 100644 index 000000000..a14be11dc --- /dev/null +++ b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDirectProxyObjectHandler.html @@ -0,0 +1,510 @@ + + + + + +JavetDirectProxyObjectHandler (javet 2.2.0 API) + + + + + + + + + + + +
    +
    com.caoccao.javet.interop.proxy
    +

    Class JavetDirectProxyObjectHandler<T extends IJavetDirectProxyHandler<E>,E extends java.lang.Exception>

    +
    +
    + +
    + +
    +
    + +
    +
    +
      +
    • + +
        +
      • + + +

        Constructor Detail

        + + + + + +
          +
        • +

          JavetDirectProxyObjectHandler

          +
          public JavetDirectProxyObjectHandler(V8Runtime v8Runtime,
          +                                     T targetObject)
          +
          Instantiates a new Base javet direct proxy object handler.
          +
          +
          Parameters:
          +
          v8Runtime - the V8 runtime
          +
          targetObject - the target object
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        +
      • +
      + +
        +
      • + + +

        Method Detail

        + + + +
          +
        • +

          get

          +
          public V8Value get(V8Value target,
          +                   V8Value property,
          +                   V8Value receiver)
          +            throws JavetException,
          +                   E extends java.lang.Exception
          +
          Description copied from interface: IJavetProxyHandler
          +
          Get by property.
          +
          +
          Parameters:
          +
          target - the target
          +
          property - the property
          +
          receiver - the receiver
          +
          Returns:
          +
          the V8 value
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          +
        • +
        + + + +
          +
        • +

          getCallbackContexts

          +
          public JavetCallbackContext[] getCallbackContexts()
          +
          Description copied from interface: IJavetDirectCallable
          +
          Get supported callback contexts.
          +
          +
          Returns:
          +
          the supported callback contexts
          +
          +
        • +
        + + + +
          +
        • +

          has

          +
          public V8ValueBoolean has(V8Value target,
          +                          V8Value property)
          +                   throws JavetException,
          +                          E extends java.lang.Exception
          +
          Description copied from interface: IJavetProxyHandler
          +
          Has property
          +
          +
          Parameters:
          +
          target - the target
          +
          property - the property
          +
          Returns:
          +
          the V8 value boolean
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          +
        • +
        + + + +
          +
        • +

          ownKeys

          +
          public V8ValueArray ownKeys(V8Value target)
          +                     throws JavetException,
          +                            E extends java.lang.Exception
          +
          Description copied from interface: IJavetProxyHandler
          +
          Own keys.
          +
          +
          Parameters:
          +
          target - the target
          +
          Returns:
          +
          the V8 value array
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          +
        • +
        + + + +
          +
        • +

          set

          +
          public V8ValueBoolean set(V8Value target,
          +                          V8Value propertyKey,
          +                          V8Value propertyValue,
          +                          V8Value receiver)
          +                   throws JavetException,
          +                          E extends java.lang.Exception
          +
          Description copied from interface: IJavetProxyHandler
          +
          Set value by property.
          +
          +
          Parameters:
          +
          target - the target
          +
          propertyKey - the property key
          +
          propertyValue - the property value
          +
          receiver - the receiver
          +
          Returns:
          +
          the V8 value boolean
          +
          Throws:
          +
          JavetException - the javet exception
          +
          E - the custom exception
          +
          E extends java.lang.Exception
          +
          +
        • +
        +
      • +
      +
    • +
    +
    +
    + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyClassHandler.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyClassHandler.html deleted file mode 100644 index 1540f52e9..000000000 --- a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyClassHandler.html +++ /dev/null @@ -1,604 +0,0 @@ - - - - - -JavetDynamicProxyClassHandler (javet 2.1.2 API) - - - - - - - - - - - -
    -
    com.caoccao.javet.interop.proxy
    -

    Class JavetDynamicProxyClassHandler<T extends java.lang.Class<?>>

    -
    -
    - -
    -
      -
    • -
      -
      Type Parameters:
      -
      T - the type parameter
      -
      -
      -
      All Implemented Interfaces:
      -
      IJavetProxyHandler<T>
      -
      -
      -
      -
      public class JavetDynamicProxyClassHandler<T extends java.lang.Class<?>>
      -extends BaseJavetProxyHandler<T>
      -
      The type Javet dynamic proxy class handler.
      -
      -
      Since:
      -
      1.1.7
      -
      -
    • -
    -
    -
    - -
    -
    - -
    -
    - - - - - - - diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyFunctionHandler.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyFunctionHandler.html deleted file mode 100644 index 76b028fc8..000000000 --- a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyFunctionHandler.html +++ /dev/null @@ -1,408 +0,0 @@ - - - - - -JavetDynamicProxyFunctionHandler (javet 2.1.2 API) - - - - - - - - - - - -
    -
    com.caoccao.javet.interop.proxy
    -

    Class JavetDynamicProxyFunctionHandler<T>

    -
    -
    - -
    -
      -
    • -
      -
      Type Parameters:
      -
      T - the type parameter
      -
      -
      -
      All Implemented Interfaces:
      -
      IJavetProxyHandler<T>
      -
      -
      -
      -
      public class JavetDynamicProxyFunctionHandler<T>
      -extends JavetDynamicProxyObjectHandler<T>
      -
      The type Javet dynamic proxy function handler.
      -
      -
      Since:
      -
      1.1.7
      -
      -
    • -
    -
    -
    - -
    -
    -
      -
    • - -
        -
      • - - -

        Field Detail

        - - - -
          -
        • -

          METHOD_NAME_APPLY

          -
          protected static final java.lang.String METHOD_NAME_APPLY
          -
          The constant METHOD_NAME_APPLY.
          -
          -
          Since:
          -
          1.1.7
          -
          See Also:
          -
          Constant Field Values
          -
          -
        • -
        -
      • -
      - -
        -
      • - - -

        Constructor Detail

        - - - - - -
          -
        • -

          JavetDynamicProxyFunctionHandler

          -
          public JavetDynamicProxyFunctionHandler(V8Runtime v8Runtime,
          -                                        IJavetDynamicObjectFactory dynamicObjectFactory,
          -                                        T targetObject)
          -
          Instantiates a new Javet dynamic proxy function handler.
          -
          -
          Parameters:
          -
          v8Runtime - the V8 runtime
          -
          dynamicObjectFactory - the dynamic object factory
          -
          targetObject - the target object
          -
          Since:
          -
          1.1.7
          -
          -
        • -
        -
      • -
      - - -
    • -
    -
    -
    - - - - - - - diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetProxySymbolIterableConverter.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetProxySymbolIterableConverter.html index af3ba5a73..431b2824a 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetProxySymbolIterableConverter.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetProxySymbolIterableConverter.html @@ -3,7 +3,7 @@ -JavetProxySymbolIterableConverter (javet 2.1.2 API) +JavetProxySymbolIterableConverter (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ + + + + + + + + + +
    +
    com.caoccao.javet.interop.proxy
    +

    Class JavetReflectionProxyClassHandler<T extends java.lang.Class<?>,E extends java.lang.Exception>

    +
    +
    + +
    +
      +
    • +
      +
      Type Parameters:
      +
      T - the type parameter
      +
      +
      +
      All Implemented Interfaces:
      +
      IJavetDirectCallable, IJavetProxyHandler<T,E>
      +
      +
      +
      +
      public class JavetReflectionProxyClassHandler<T extends java.lang.Class<?>,E extends java.lang.Exception>
      +extends BaseJavetReflectionProxyHandler<T,E>
      +
      The type Javet reflection proxy class handler.
      +
      +
      Since:
      +
      1.1.7
      +
      +
    • +
    +
    +
    + +
    +
    +
      +
    • + +
        +
      • + + +

        Field Detail

        + + + +
          +
        • +

          METHOD_NAME_CONSTRUCTOR

          +
          protected static final java.lang.String METHOD_NAME_CONSTRUCTOR
          +
          The constant METHOD_NAME_CONSTRUCTOR.
          +
          +
          Since:
          +
          0.9.8
          +
          See Also:
          +
          Constant Field Values
          +
          +
        • +
        + + + +
          +
        • +

          classDescriptorMap

          +
          protected static final ThreadSafeMap<java.lang.Class<?>,ClassDescriptor> classDescriptorMap
          +
          The constant classDescriptorMap.
          +
          +
          Since:
          +
          1.1.7
          +
          +
        • +
        +
      • +
      + +
        +
      • + + +

        Constructor Detail

        + + + + + +
          +
        • +

          JavetReflectionProxyClassHandler

          +
          public JavetReflectionProxyClassHandler(V8Runtime v8Runtime,
          +                                        IJavetReflectionObjectFactory reflectionObjectFactory,
          +                                        T targetObject)
          +
          Instantiates a new Javet reflection proxy handler.
          +
          +
          Parameters:
          +
          v8Runtime - the V8 runtime
          +
          reflectionObjectFactory - the reflection object factory
          +
          targetObject - the target object
          +
          Since:
          +
          0.9.6
          +
          +
        • +
        +
      • +
      + + +
    • +
    +
    +
    + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyFactory.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetReflectionProxyFactory.html similarity index 77% rename from docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyFactory.html rename to docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetReflectionProxyFactory.html index 9fd52b6e0..0b729f860 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyFactory.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetReflectionProxyFactory.html @@ -3,7 +3,7 @@ -JavetDynamicProxyFactory (javet 2.1.2 API) +JavetReflectionProxyFactory (javet 2.2.0 API) @@ -11,7 +11,7 @@ + + + + + + + + + +
    +
    com.caoccao.javet.interop.proxy
    +

    Class JavetReflectionProxyFunctionHandler<T,E extends java.lang.Exception>

    +
    +
    + +
    +
      +
    • +
      +
      Type Parameters:
      +
      T - the type parameter
      +
      E - the type parameter
      +
      +
      +
      All Implemented Interfaces:
      +
      IJavetDirectCallable, IJavetProxyHandler<T,E>
      +
      +
      +
      +
      public class JavetReflectionProxyFunctionHandler<T,E extends java.lang.Exception>
      +extends JavetReflectionProxyObjectHandler<T,E>
      +
      The type Javet reflection proxy function handler.
      +
      +
      Since:
      +
      1.1.7
      +
      +
    • +
    +
    +
    + +
    +
    + +
    +
    + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyObjectHandler.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetReflectionProxyObjectHandler.html similarity index 51% rename from docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyObjectHandler.html rename to docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetReflectionProxyObjectHandler.html index 6340a08f3..ae67bf6ba 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetDynamicProxyObjectHandler.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/JavetReflectionProxyObjectHandler.html @@ -3,7 +3,7 @@ -JavetDynamicProxyObjectHandler (javet 2.1.2 API) +JavetReflectionProxyObjectHandler (javet 2.2.0 API) @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -12,22 +12,27 @@

    Interfaces

    Classes

    diff --git a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/package-summary.html index b08192801..149f77276 100644 --- a/docs/reference/javadoc/com/caoccao/javet/interop/proxy/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/interop/proxy/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.interop.proxy (javet 2.1.2 API) +com.caoccao.javet.interop.proxy (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/node/modules/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/node/modules/package-summary.html index 7b23de262..82f0dab72 100644 --- a/docs/reference/javadoc/com/caoccao/javet/node/modules/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/node/modules/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.node.modules (javet 2.1.2 API) +com.caoccao.javet.node.modules (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/utils/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/utils/package-summary.html index 901a1757a..467361db1 100644 --- a/docs/reference/javadoc/com/caoccao/javet/utils/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/utils/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.utils (javet 2.1.2 API) +com.caoccao.javet.utils (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/utils/receivers/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/utils/receivers/package-summary.html index 0dc5f3c5e..5c4dc638f 100644 --- a/docs/reference/javadoc/com/caoccao/javet/utils/receivers/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/utils/receivers/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.utils.receivers (javet 2.1.2 API) +com.caoccao.javet.utils.receivers (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/values/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/values/package-summary.html index 3b7bbe619..0d313f210 100644 --- a/docs/reference/javadoc/com/caoccao/javet/values/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/values/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.values (javet 2.1.2 API) +com.caoccao.javet.values (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/values/primitive/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/values/primitive/package-summary.html index d1bb98504..693636d7c 100644 --- a/docs/reference/javadoc/com/caoccao/javet/values/primitive/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/values/primitive/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.values.primitive (javet 2.1.2 API) +com.caoccao.javet.values.primitive (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ + + + + + + + + + +
    +
    com.caoccao.javet.values.reference
    +

    Interface IV8Cacheable

    +
    +
    +
    + +
    +
    + +
    +
    +
      +
    • + +
        +
      • + + +

        Method Detail

        + + + +
          +
        • +

          getCachedData

          +
          byte[] getCachedData()
          +              throws JavetException
          +
          Gets cached data.
          +
          +
          Returns:
          +
          the cached data
          +
          Throws:
          +
          JavetException - the javet exception
          +
          Since:
          +
          2.2.0
          +
          +
        • +
        +
      • +
      +
    • +
    +
    +
    + + + + + + + diff --git a/docs/reference/javadoc/com/caoccao/javet/values/reference/IV8Context.html b/docs/reference/javadoc/com/caoccao/javet/values/reference/IV8Context.html index 04920a175..cd4d69fbd 100644 --- a/docs/reference/javadoc/com/caoccao/javet/values/reference/IV8Context.html +++ b/docs/reference/javadoc/com/caoccao/javet/values/reference/IV8Context.html @@ -3,7 +3,7 @@ -IV8Context (javet 2.1.2 API) +IV8Context (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,13 +11,13 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,13 +11,13 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/values/reference/builtin/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/values/reference/builtin/package-summary.html index 422361673..c2a85ce52 100644 --- a/docs/reference/javadoc/com/caoccao/javet/values/reference/builtin/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/values/reference/builtin/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.values.reference.builtin (javet 2.1.2 API) +com.caoccao.javet.values.reference.builtin (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -12,6 +12,7 @@

    Interfaces

      +
    • IV8Cacheable
    • IV8Context
    • IV8Module
    • IV8Script
    • diff --git a/docs/reference/javadoc/com/caoccao/javet/values/reference/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/values/reference/package-summary.html index 182f97b2c..bb6e87bc7 100644 --- a/docs/reference/javadoc/com/caoccao/javet/values/reference/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/values/reference/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.values.reference (javet 2.1.2 API) +com.caoccao.javet.values.reference (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/com/caoccao/javet/values/virtual/package-summary.html b/docs/reference/javadoc/com/caoccao/javet/values/virtual/package-summary.html index ce771f6d2..ff000f9e9 100644 --- a/docs/reference/javadoc/com/caoccao/javet/values/virtual/package-summary.html +++ b/docs/reference/javadoc/com/caoccao/javet/values/virtual/package-summary.html @@ -3,7 +3,7 @@ -com.caoccao.javet.values.virtual (javet 2.1.2 API) +com.caoccao.javet.values.virtual (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ diff --git a/docs/reference/javadoc/overview-summary.html b/docs/reference/javadoc/overview-summary.html index 4d3b429ef..67e5db796 100644 --- a/docs/reference/javadoc/overview-summary.html +++ b/docs/reference/javadoc/overview-summary.html @@ -3,7 +3,7 @@ -Overview (javet 2.1.2 API) +Overview (javet 2.2.0 API) @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ @@ -11,7 +11,7 @@ + + + + Contents + + + + + + + + + Menu + + + + + + + + Expand + + + + + + Light mode + + + + + + + + + + + + + + Dark mode + + + + + + + Auto light/dark mode + + + + + + + + + + + + + + + + + + + +
      +
      +
      + +
      + +
      +
      + +
      + +
      +
      + +
      +
      +
      +
      +
      + +
      + +
      +
      +
      +

      Release Notes 2.2.x

      +
      +

      2.2.0 V8 v11.4

      +
        +
      • Upgraded V8 to v11.4.183.14 (2023-05-23)

      • +
      • Improved the performance of V8FunctionCallback.receiveCallback(), IV8ValueObject.forEach(), IV8ValueMap.forEach(), IV8ValueArray.forEach(), IV8ValueArray.push(), IV8ValueObject.set(), IV8ValueMap.set(),

      • +
      • Added IV8ValueObject.batchGet(), IV8ValueMap.batchGet(), IV8ValueArray.batchGet()

      • +
      • Added JavetCallbackType, IJavetDirectCallable, IJavetDirectProxyHandler to allow callback without reflection

      • +
      • Redesigned IV8ValueObject.bindFunction(), IV8ValueObject.bindProperty(), IV8ValueObject.unbindFunction(), IV8ValueObject.unbindProperty(), JavetCallbackContext

      • +
      • Renamed JavetDynamicProxy* to JavetReflectionProxy*

      • +
      • Added error code 408 CallbackTypeNotSupported

      • +
      • Created JavetPerf for tracking the performance among various Javet releases

      • +
      +
      +
      + +
      +
      + +
      + +
      +
      + + + + + + + \ No newline at end of file diff --git a/docs/release_notes/release_notes_2_2.rst b/docs/release_notes/release_notes_2_2.rst new file mode 100644 index 000000000..9e8d63d49 --- /dev/null +++ b/docs/release_notes/release_notes_2_2.rst @@ -0,0 +1,15 @@ +=================== +Release Notes 2.2.x +=================== + +2.2.0 V8 v11.4 +-------------- + +* Upgraded V8 to ``v11.4.183.14`` (2023-05-23) +* Improved the performance of ``V8FunctionCallback.receiveCallback()``, ``IV8ValueObject.forEach()``, ``IV8ValueMap.forEach()``, ``IV8ValueArray.forEach()``, ``IV8ValueArray.push()``, ``IV8ValueObject.set()``, ``IV8ValueMap.set()``, +* Added ``IV8ValueObject.batchGet()``, ``IV8ValueMap.batchGet()``, ``IV8ValueArray.batchGet()`` +* Added ``JavetCallbackType``, ``IJavetDirectCallable``, ``IJavetDirectProxyHandler`` to allow callback without reflection +* Redesigned ``IV8ValueObject.bindFunction()``, ``IV8ValueObject.bindProperty()``, ``IV8ValueObject.unbindFunction()``, ``IV8ValueObject.unbindProperty()``, ``JavetCallbackContext`` +* Renamed ``JavetDynamicProxy*`` to ``JavetReflectionProxy*`` +* Added error code 408 CallbackTypeNotSupported +* Created `JavetPerf `_ for tracking the performance among various Javet releases diff --git a/docs/search.html b/docs/search.html index be6432cb8..db01d11d8 100644 --- a/docs/search.html +++ b/docs/search.html @@ -4,7 +4,7 @@ - Search - Javet 2.1.2 documentation + Search - Javet 2.2.0 documentation @@ -122,7 +122,7 @@

    @@ -148,7 +148,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/advanced/interact_with_node_js.html b/docs/tutorial/advanced/interact_with_node_js.html index ea476b107..d94e2025b 100644 --- a/docs/tutorial/advanced/interact_with_node_js.html +++ b/docs/tutorial/advanced/interact_with_node_js.html @@ -5,7 +5,7 @@ - Interact with Node.js - Javet 2.1.2 documentation + Interact with Node.js - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/advanced/java_and_javascript_interop.html b/docs/tutorial/advanced/java_and_javascript_interop.html index fbb30dd83..7221d7288 100644 --- a/docs/tutorial/advanced/java_and_javascript_interop.html +++ b/docs/tutorial/advanced/java_and_javascript_interop.html @@ -5,7 +5,7 @@ - Java and JavaScript Interop - Javet 2.1.2 documentation + Java and JavaScript Interop - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/advanced/object_converter.html b/docs/tutorial/advanced/object_converter.html index 77f9a8f0a..3c0f99ac3 100644 --- a/docs/tutorial/advanced/object_converter.html +++ b/docs/tutorial/advanced/object_converter.html @@ -5,7 +5,7 @@ - Object Converter - Javet 2.1.2 documentation + Object Converter - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/basic/engine_pool.html b/docs/tutorial/basic/engine_pool.html index 35a9bdbdc..34d9226b1 100644 --- a/docs/tutorial/basic/engine_pool.html +++ b/docs/tutorial/basic/engine_pool.html @@ -5,7 +5,7 @@ - Javet Engine Pool - Javet 2.1.2 documentation + Javet Engine Pool - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/basic/hello_javet.html b/docs/tutorial/basic/hello_javet.html index 91db9b46e..d2c595365 100644 --- a/docs/tutorial/basic/hello_javet.html +++ b/docs/tutorial/basic/hello_javet.html @@ -5,7 +5,7 @@ - Hello Javet - Javet 2.1.2 documentation + Hello Javet - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/basic/index.html b/docs/tutorial/basic/index.html index 9d5ee9458..155d4e31c 100644 --- a/docs/tutorial/basic/index.html +++ b/docs/tutorial/basic/index.html @@ -5,7 +5,7 @@ - Basic - Javet 2.1.2 documentation + Basic - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/basic/installation.html b/docs/tutorial/basic/installation.html index 49961d5a8..5bc653345 100644 --- a/docs/tutorial/basic/installation.html +++ b/docs/tutorial/basic/installation.html @@ -5,7 +5,7 @@ - Installation - Javet 2.1.2 documentation + Installation - Javet 2.2.0 documentation @@ -124,7 +124,7 @@

    Gradle Kotlin DSL

    -
    implementation("com.caoccao.javet:javet:2.1.2") // Linux and Windows (x86_64)
    -implementation("com.caoccao.javet:javet-macos:2.1.2") // Mac OS (x86_64 and arm64)
    -implementation("com.caoccao.javet:javet-android:2.1.2") // Android (arm, arm64, x86 and x86_64)
    +
    implementation("com.caoccao.javet:javet:2.2.0") // Linux and Windows (x86_64)
    +implementation("com.caoccao.javet:javet-macos:2.2.0") // Mac OS (x86_64 and arm64)
    +implementation("com.caoccao.javet:javet-android:2.2.0") // Android (arm, arm64, x86 and x86_64)
     

    Gradle Groovy DSL

    -
    implementation 'com.caoccao.javet:javet:2.1.2' // Linux and Windows (x86_64)
    -implementation 'com.caoccao.javet:javet-macos:2.1.2' // Mac OS (x86_64 and arm64)
    -implementation 'com.caoccao.javet:javet-android:2.1.2' // Android (arm, arm64, x86 and x86_64)
    +
    implementation 'com.caoccao.javet:javet:2.2.0' // Linux and Windows (x86_64)
    +implementation 'com.caoccao.javet:javet-macos:2.2.0' // Mac OS (x86_64 and arm64)
    +implementation 'com.caoccao.javet:javet-android:2.2.0' // Android (arm, arm64, x86 and x86_64)
     
    diff --git a/docs/tutorial/basic/installation.rst b/docs/tutorial/basic/installation.rst index cd7f17cc6..3eaf3cf65 100644 --- a/docs/tutorial/basic/installation.rst +++ b/docs/tutorial/basic/installation.rst @@ -14,14 +14,14 @@ Maven com.caoccao.javet javet - 2.1.2 + 2.2.0 com.caoccao.javet javet-macos - 2.1.2 + 2.2.0 Gradle Kotlin DSL @@ -29,18 +29,18 @@ Gradle Kotlin DSL .. code-block:: kotlin - implementation("com.caoccao.javet:javet:2.1.2") // Linux and Windows (x86_64) - implementation("com.caoccao.javet:javet-macos:2.1.2") // Mac OS (x86_64 and arm64) - implementation("com.caoccao.javet:javet-android:2.1.2") // Android (arm, arm64, x86 and x86_64) + implementation("com.caoccao.javet:javet:2.2.0") // Linux and Windows (x86_64) + implementation("com.caoccao.javet:javet-macos:2.2.0") // Mac OS (x86_64 and arm64) + implementation("com.caoccao.javet:javet-android:2.2.0") // Android (arm, arm64, x86 and x86_64) Gradle Groovy DSL ----------------- .. code-block:: groovy - implementation 'com.caoccao.javet:javet:2.1.2' // Linux and Windows (x86_64) - implementation 'com.caoccao.javet:javet-macos:2.1.2' // Mac OS (x86_64 and arm64) - implementation 'com.caoccao.javet:javet-android:2.1.2' // Android (arm, arm64, x86 and x86_64) + implementation 'com.caoccao.javet:javet:2.2.0' // Linux and Windows (x86_64) + implementation 'com.caoccao.javet:javet-macos:2.2.0' // Mac OS (x86_64 and arm64) + implementation 'com.caoccao.javet:javet-android:2.2.0' // Android (arm, arm64, x86 and x86_64) OS Compatibility ================ diff --git a/docs/tutorial/basic/interception.html b/docs/tutorial/basic/interception.html index 649d0a6ca..6a7a0cca6 100644 --- a/docs/tutorial/basic/interception.html +++ b/docs/tutorial/basic/interception.html @@ -5,7 +5,7 @@ - Interception - Javet 2.1.2 documentation + Interception - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/basic/javet_shell.html b/docs/tutorial/basic/javet_shell.html index fe21e8883..42d610fbc 100644 --- a/docs/tutorial/basic/javet_shell.html +++ b/docs/tutorial/basic/javet_shell.html @@ -5,7 +5,7 @@ - Javet Shell - Javet 2.1.2 documentation + Javet Shell - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/basic/node_js_mode_and_v8_mode.html b/docs/tutorial/basic/node_js_mode_and_v8_mode.html index 1a9bc6aa5..bc1124aa1 100644 --- a/docs/tutorial/basic/node_js_mode_and_v8_mode.html +++ b/docs/tutorial/basic/node_js_mode_and_v8_mode.html @@ -5,7 +5,7 @@ - Node.js Mode and V8 Mode - Javet 2.1.2 documentation + Node.js Mode and V8 Mode - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/basic/polyfill.html b/docs/tutorial/basic/polyfill.html index 1986a0471..cb4fc5dd5 100644 --- a/docs/tutorial/basic/polyfill.html +++ b/docs/tutorial/basic/polyfill.html @@ -5,7 +5,7 @@ - Polyfill - Javet 2.1.2 documentation + Polyfill - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/basic/spring_integration.html b/docs/tutorial/basic/spring_integration.html index 731d01f00..706e68e07 100644 --- a/docs/tutorial/basic/spring_integration.html +++ b/docs/tutorial/basic/spring_integration.html @@ -5,7 +5,7 @@ - Spring Integration - Javet 2.1.2 documentation + Spring Integration - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/index.html b/docs/tutorial/index.html index c1376a774..e0046aca1 100644 --- a/docs/tutorial/index.html +++ b/docs/tutorial/index.html @@ -5,7 +5,7 @@ - Tutorial - Javet 2.1.2 documentation + Tutorial - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/migration_guides/index.html b/docs/tutorial/migration_guides/index.html index a1350b0e8..67f50b746 100644 --- a/docs/tutorial/migration_guides/index.html +++ b/docs/tutorial/migration_guides/index.html @@ -5,7 +5,7 @@ - Migration Guides - Javet 2.1.2 documentation + Migration Guides - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/docs/tutorial/migration_guides/migrate_from_j2v8.html b/docs/tutorial/migration_guides/migrate_from_j2v8.html index 8d1b4ca19..ca082f069 100644 --- a/docs/tutorial/migration_guides/migrate_from_j2v8.html +++ b/docs/tutorial/migration_guides/migrate_from_j2v8.html @@ -5,7 +5,7 @@ - Migrate from J2V8 - Javet 2.1.2 documentation + Migrate from J2V8 - Javet 2.2.0 documentation @@ -124,7 +124,7 @@
    @@ -150,7 +150,7 @@
    - Javet 2.1.2 documentation + Javet 2.2.0 documentation @@ -221,7 +221,7 @@
  • Release Notes
  • FAQ
  • diff --git a/pom.xml b/pom.xml index 2e37a8d4c..fccb11183 100644 --- a/pom.xml +++ b/pom.xml @@ -3,7 +3,7 @@ com.caoccao.javet javet - 2.1.2 + 2.2.0 javet Javet is Java + V8 (JAVa + V + EighT). It is an awesome way of embedding V8 in Java. https://github.com/caoccao/Javet @@ -28,7 +28,7 @@ scm:git:git://github.com/caoccao/Javet.git scm:git:git@github.com:caoccao/caoccao.git https://github.com/caoccao/Javet - 2.1.2 + 2.2.0 diff --git a/scripts/node/javet-rebuild/rebuild.cmd b/scripts/node/javet-rebuild/rebuild.cmd index ee8bb49d3..ca4aa1b20 100644 --- a/scripts/node/javet-rebuild/rebuild.cmd +++ b/scripts/node/javet-rebuild/rebuild.cmd @@ -1,5 +1,5 @@ @echo off -SET NODE_LIB_FILE="..\..\..\..\..\..\build\libs\libjavet-node-windows-x86_64.v.2.1.2.lib" +SET NODE_LIB_FILE="..\..\..\..\..\..\build\libs\libjavet-node-windows-x86_64.v.2.2.0.lib" cd %NODE_MODULE_ROOT% call node-gyp clean call node-gyp configure --module_name=%NODE_MODULE_NAME% --module_path=%NODE_MODULE_PATH% --node_lib_file=%NODE_LIB_FILE% diff --git a/scripts/node/javet-rebuild/rebuild.sh b/scripts/node/javet-rebuild/rebuild.sh index 14d0f13f5..eac0f08eb 100755 --- a/scripts/node/javet-rebuild/rebuild.sh +++ b/scripts/node/javet-rebuild/rebuild.sh @@ -1 +1 @@ -patchelf --add-needed libjavet-node-linux-x86_64.v.2.1.2.so ${NODE_MODULE_FILE} +patchelf --add-needed libjavet-node-linux-x86_64.v.2.2.0.so ${NODE_MODULE_FILE} diff --git a/scripts/python/change_javet_version.py b/scripts/python/change_javet_version.py index 2c430cea8..54a2b1073 100644 --- a/scripts/python/change_javet_version.py +++ b/scripts/python/change_javet_version.py @@ -168,7 +168,7 @@ def _update(self, relative_file_path: str, line_separator: str, *patterns: list) logging.info(' Updated.') def main(): - change_javet_version = ChangeJavetVersion('2.1.2') + change_javet_version = ChangeJavetVersion('2.2.0') change_javet_version.update() return 0 diff --git a/scripts/python/change_node_v8_version.py b/scripts/python/change_node_v8_version.py index c9cf9cd8e..423daa224 100644 --- a/scripts/python/change_node_v8_version.py +++ b/scripts/python/change_node_v8_version.py @@ -136,7 +136,7 @@ def update(self) -> None: def main(): change_node_version = ChangeNodeVersion('18.16.0') change_node_version.update() - change_v8_version = ChangeV8Version('11.3.244.8') + change_v8_version = ChangeV8Version('11.4.183.14') change_v8_version.update() return 0 diff --git a/src/main/java/com/caoccao/javet/annotations/V8Convert.java b/src/main/java/com/caoccao/javet/annotations/V8Convert.java index 7d58a6d2a..c825c02d3 100644 --- a/src/main/java/com/caoccao/javet/annotations/V8Convert.java +++ b/src/main/java/com/caoccao/javet/annotations/V8Convert.java @@ -38,5 +38,11 @@ */ V8ConversionMode mode() default V8ConversionMode.Transparent; + /** + * Proxy mode. + * + * @return the proxy mode + * @since 1.1.7 + */ V8ProxyMode proxyMode() default V8ProxyMode.Object; } diff --git a/src/main/java/com/caoccao/javet/enums/JSRuntimeType.java b/src/main/java/com/caoccao/javet/enums/JSRuntimeType.java index 8461c9480..a6f5cd538 100644 --- a/src/main/java/com/caoccao/javet/enums/JSRuntimeType.java +++ b/src/main/java/com/caoccao/javet/enums/JSRuntimeType.java @@ -47,7 +47,7 @@ public enum JSRuntimeType { */ V8( "v8", - "11.3.244.8", + "11.4.183.14", V8RuntimeOptions::new, o -> o instanceof V8RuntimeOptions); diff --git a/src/main/java/com/caoccao/javet/exceptions/JavetError.java b/src/main/java/com/caoccao/javet/exceptions/JavetError.java index c469aefd6..f818935d6 100644 --- a/src/main/java/com/caoccao/javet/exceptions/JavetError.java +++ b/src/main/java/com/caoccao/javet/exceptions/JavetError.java @@ -28,11 +28,11 @@ */ public class JavetError { /** - * The constant PARAMETER_EXPECTED_PARAMETER_TYPE. + * The constant PARAMETER_ACTUAL_PARAMETER_SIZE. * * @since 0.8.5 */ - public static final String PARAMETER_EXPECTED_PARAMETER_TYPE = "expectedParameterType"; + public static final String PARAMETER_ACTUAL_PARAMETER_SIZE = "actualParameterSize"; /** * The constant PARAMETER_ACTUAL_PARAMETER_TYPE. * @@ -40,138 +40,143 @@ public class JavetError { */ public static final String PARAMETER_ACTUAL_PARAMETER_TYPE = "actualParameterType"; /** - * The constant PARAMETER_METHOD_NAME. + * The constant PARAMETER_CALLBACK_TYPE. * - * @since 0.8.5 + * @since 2.2.0 */ - public static final String PARAMETER_METHOD_NAME = "methodName"; + public static final String PARAMETER_CALLBACK_TYPE = "callbackType"; /** - * The constant PARAMETER_EXPECTED_PARAMETER_SIZE. + * The constant PARAMETER_CONTINUABLE. * * @since 0.8.5 */ - public static final String PARAMETER_EXPECTED_PARAMETER_SIZE = "expectedParameterSize"; + public static final String PARAMETER_CONTINUABLE = "continuable"; /** - * The constant PARAMETER_ACTUAL_PARAMETER_SIZE. + * The constant PARAMETER_COUNT. * * @since 0.8.5 */ - public static final String PARAMETER_ACTUAL_PARAMETER_SIZE = "actualParameterSize"; + public static final String PARAMETER_COUNT = "count"; /** - * The constant PARAMETER_RESOURCE_NAME. + * The constant PARAMETER_CURRENT_THREAD_ID. * * @since 0.8.5 */ - public static final String PARAMETER_RESOURCE_NAME = "resourceName"; + public static final String PARAMETER_CURRENT_THREAD_ID = "currentThreadId"; /** - * The constant PARAMETER_SOURCE_LINE. + * The constant PARAMETER_END_COLUMN. * * @since 0.8.5 */ - public static final String PARAMETER_SOURCE_LINE = "sourceLine"; + public static final String PARAMETER_END_COLUMN = "endColumn"; /** - * The constant PARAMETER_LINE_NUMBER. + * The constant PARAMETER_END_POSITION. * * @since 0.8.5 */ - public static final String PARAMETER_LINE_NUMBER = "lineNumber"; + public static final String PARAMETER_END_POSITION = "endPosition"; /** - * The constant PARAMETER_START_COLUMN. + * The constant PARAMETER_EXPECTED_PARAMETER_SIZE. * * @since 0.8.5 */ - public static final String PARAMETER_START_COLUMN = "startColumn"; + public static final String PARAMETER_EXPECTED_PARAMETER_SIZE = "expectedParameterSize"; /** - * The constant PARAMETER_END_COLUMN. + * The constant PARAMETER_EXPECTED_PARAMETER_TYPE. * * @since 0.8.5 */ - public static final String PARAMETER_END_COLUMN = "endColumn"; + public static final String PARAMETER_EXPECTED_PARAMETER_TYPE = "expectedParameterType"; /** - * The constant PARAMETER_START_POSITION. + * The constant PARAMETER_FEATURE. * * @since 0.8.5 */ - public static final String PARAMETER_START_POSITION = "startPosition"; + public static final String PARAMETER_FEATURE = "feature"; /** - * The constant PARAMETER_END_POSITION. + * The constant PARAMETER_HEAP_STATISTICS. + * + * @since 1.0.4 + */ + public static final String PARAMETER_HEAP_STATISTICS = "heapStatistics"; + /** + * The constant PARAMETER_LINE_NUMBER. * * @since 0.8.5 */ - public static final String PARAMETER_END_POSITION = "endPosition"; + public static final String PARAMETER_LINE_NUMBER = "lineNumber"; /** - * The constant PARAMETER_MESSAGE. + * The constant PARAMETER_LOCKED_THREAD_ID. * * @since 0.8.5 */ - public static final String PARAMETER_MESSAGE = "message"; + public static final String PARAMETER_LOCKED_THREAD_ID = "lockedThreadId"; /** - * The constant PARAMETER_CURRENT_THREAD_ID. + * The constant PARAMETER_MAX_DEPTH. * * @since 0.8.5 */ - public static final String PARAMETER_CURRENT_THREAD_ID = "currentThreadId"; + public static final String PARAMETER_MAX_DEPTH = "maxDepth"; /** - * The constant PARAMETER_LOCKED_THREAD_ID. + * The constant PARAMETER_MESSAGE. * * @since 0.8.5 */ - public static final String PARAMETER_LOCKED_THREAD_ID = "lockedThreadId"; + public static final String PARAMETER_MESSAGE = "message"; /** - * The constant PARAMETER_OS. + * The constant PARAMETER_METHOD_NAME. * * @since 0.8.5 */ - public static final String PARAMETER_OS = "OS"; + public static final String PARAMETER_METHOD_NAME = "methodName"; /** - * The constant PARAMETER_FEATURE. + * The constant PARAMETER_OS. * * @since 0.8.5 */ - public static final String PARAMETER_FEATURE = "feature"; + public static final String PARAMETER_OS = "OS"; /** - * The constant PARAMETER_SYMBOL. + * The constant PARAMETER_PATH. * * @since 0.8.5 */ - public static final String PARAMETER_SYMBOL = "symbol"; + public static final String PARAMETER_PATH = "path"; /** - * The constant PARAMETER_COUNT. + * The constant PARAMETER_REASON. * * @since 0.8.5 */ - public static final String PARAMETER_COUNT = "count"; + public static final String PARAMETER_REASON = "reason"; /** - * The constant PARAMETER_CONTINUABLE. + * The constant PARAMETER_RESOURCE_NAME. * * @since 0.8.5 */ - public static final String PARAMETER_CONTINUABLE = "continuable"; + public static final String PARAMETER_RESOURCE_NAME = "resourceName"; /** - * The constant PARAMETER_PATH. + * The constant PARAMETER_SOURCE_LINE. * * @since 0.8.5 */ - public static final String PARAMETER_PATH = "path"; + public static final String PARAMETER_SOURCE_LINE = "sourceLine"; /** - * The constant PARAMETER_REASON. + * The constant PARAMETER_START_COLUMN. * * @since 0.8.5 */ - public static final String PARAMETER_REASON = "reason"; + public static final String PARAMETER_START_COLUMN = "startColumn"; /** - * The constant PARAMETER_MAX_DEPTH. + * The constant PARAMETER_START_POSITION. * * @since 0.8.5 */ - public static final String PARAMETER_MAX_DEPTH = "maxDepth"; + public static final String PARAMETER_START_POSITION = "startPosition"; /** - * The constant PARAMETER_HEAP_STATISTICS. + * The constant PARAMETER_SYMBOL. * - * @since 1.0.4 + * @since 0.8.5 */ - public static final String PARAMETER_HEAP_STATISTICS = "heapStatistics"; - + public static final String PARAMETER_SYMBOL = "symbol"; /** * The constant OSNotSupported. * @@ -207,7 +212,6 @@ public class JavetError { */ public static final JavetError FailedToReadPath = new JavetError( 105, JavetErrorType.System, "Failed to read ${path}"); - /** * The constant CompilationFailure. * @@ -215,7 +219,6 @@ public class JavetError { */ public static final JavetError CompilationFailure = new JavetError( 201, JavetErrorType.Compilation, "${message}"); - /** * The constant ExecutionFailure. * @@ -230,7 +233,6 @@ public class JavetError { */ public static final JavetError ExecutionTerminated = new JavetError( 302, JavetErrorType.Execution, "Execution is terminated and continuable is ${continuable}"); - /** * The constant CallbackSignatureParameterSizeMismatch. * @@ -280,7 +282,13 @@ public class JavetError { */ public static final JavetError CallbackUnregistrationFailure = new JavetError( 407, JavetErrorType.Callback, "Callback ${methodName} unregistration failed with error message ${message}"); - + /** + * The constant CallbackTypeNotSupported. + * + * @since 2.2.0 + */ + public static final JavetError CallbackTypeNotSupported = new JavetError( + 408, JavetErrorType.Callback, "Callback type ${callbackType} is not supported"); /** * The constant ConverterFailure. * @@ -302,7 +310,6 @@ public class JavetError { */ public static final JavetError ConverterSymbolNotBuiltIn = new JavetError( 503, JavetErrorType.Converter, "${symbol} is not a built-in symbol"); - /** * The constant ModuleNameEmpty. * @@ -324,7 +331,6 @@ public class JavetError { */ public static final JavetError ModulePermissionDenied = new JavetError( 603, JavetErrorType.Module, "Denied access to module ${moduleName}"); - /** * The constant LockAcquisitionFailure. * @@ -346,7 +352,6 @@ public class JavetError { */ public static final JavetError LockConflictThreadIdMismatch = new JavetError( 703, JavetErrorType.Lock, "Runtime lock conflict is detected with locked thread ID ${lockedThreadID} and current thread ID ${currentThreadID}"); - /** * The constant RuntimeAlreadyClosed. * @@ -389,7 +394,6 @@ public class JavetError { */ public static final JavetError RuntimeOutOfMemory = new JavetError( 806, JavetErrorType.Runtime, "Runtime is out of memory because ${message} with ${heapStatistics}"); - /** * The constant EngineNotAvailable. * @@ -397,7 +401,6 @@ public class JavetError { */ public static final JavetError EngineNotAvailable = new JavetError( 901, JavetErrorType.Engine, "Engine is not available."); - /** * The Code. * diff --git a/src/main/java/com/caoccao/javet/interception/logging/BaseJavetConsoleInterceptor.java b/src/main/java/com/caoccao/javet/interception/logging/BaseJavetConsoleInterceptor.java index 9b4fa6abe..3ec6b98f7 100644 --- a/src/main/java/com/caoccao/javet/interception/logging/BaseJavetConsoleInterceptor.java +++ b/src/main/java/com/caoccao/javet/interception/logging/BaseJavetConsoleInterceptor.java @@ -215,10 +215,10 @@ public boolean register(IV8ValueObject... iV8ValueObjects) throws JavetException protected void register(IV8ValueObject iV8ValueObject, String jsFunctionName, String javaFunctionName) throws JavetException { try { - iV8ValueObject.bindFunction( + iV8ValueObject.bindFunction(new JavetCallbackContext( jsFunctionName, - new JavetCallbackContext(this, - getClass().getMethod(javaFunctionName, V8Value[].class))); + this, + getClass().getMethod(javaFunctionName, V8Value[].class))); } catch (NoSuchMethodException e) { throw new JavetException( JavetError.CallbackRegistrationFailure, diff --git a/src/main/java/com/caoccao/javet/interfaces/IJavetBiConsumer.java b/src/main/java/com/caoccao/javet/interfaces/IJavetBiConsumer.java index 369897f1e..f4fa28f14 100644 --- a/src/main/java/com/caoccao/javet/interfaces/IJavetBiConsumer.java +++ b/src/main/java/com/caoccao/javet/interfaces/IJavetBiConsumer.java @@ -27,6 +27,7 @@ * @param the type parameter for custom exception * @since 0.8.9 */ +@FunctionalInterface public interface IJavetBiConsumer { /** * Accept. diff --git a/src/main/java/com/caoccao/javet/interfaces/IJavetBiFunction.java b/src/main/java/com/caoccao/javet/interfaces/IJavetBiFunction.java new file mode 100644 index 000000000..34b199a98 --- /dev/null +++ b/src/main/java/com/caoccao/javet/interfaces/IJavetBiFunction.java @@ -0,0 +1,43 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interfaces; + +import com.caoccao.javet.exceptions.JavetException; + +/** + * The interface Javet bi-function. + * + * @param the type parameter + * @param the type parameter + * @param the type parameter + * @param the type parameter + * @since 2.2.0 + */ +@FunctionalInterface +public interface IJavetBiFunction { + /** + * Apply. + * + * @param value1 the value 1 + * @param value2 the value 2 + * @return the result + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + R apply(T1 value1, T2 value2) throws JavetException, E; +} diff --git a/src/main/java/com/caoccao/javet/interfaces/IJavetBiIndexedConsumer.java b/src/main/java/com/caoccao/javet/interfaces/IJavetBiIndexedConsumer.java index a87e35a22..f8acb60fa 100644 --- a/src/main/java/com/caoccao/javet/interfaces/IJavetBiIndexedConsumer.java +++ b/src/main/java/com/caoccao/javet/interfaces/IJavetBiIndexedConsumer.java @@ -22,12 +22,13 @@ /** * The interface Javet bi-indexed consumer. * - * @param the type parameter for key - * @param the type parameter for value - * @param the type parameter for custom exception + * @param the type parameter for key + * @param the type parameter for value + * @param the type parameter for custom exception * @since 0.8.10 */ -public interface IJavetBiIndexedConsumer { +@FunctionalInterface +public interface IJavetBiIndexedConsumer { /** * Accept. * @@ -38,5 +39,5 @@ public interface IJavetBiIndexedConsumer the type parameter for custom exception * @since 0.8.10 */ +@FunctionalInterface public interface IJavetUniConsumer { /** * Accept. diff --git a/src/main/java/com/caoccao/javet/interfaces/IJavetUniFunction.java b/src/main/java/com/caoccao/javet/interfaces/IJavetUniFunction.java new file mode 100644 index 000000000..f65d9ce7e --- /dev/null +++ b/src/main/java/com/caoccao/javet/interfaces/IJavetUniFunction.java @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interfaces; + +import com.caoccao.javet.exceptions.JavetException; + +/** + * The interface Javet uni-function. + * + * @param the type parameter + * @param the type parameter + * @param the type parameter + * @since 2.2.0 + */ +@FunctionalInterface +public interface IJavetUniFunction { + /** + * Apply. + * + * @param value the value + * @return the result + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + R apply(T value) throws JavetException, E; +} diff --git a/src/main/java/com/caoccao/javet/interfaces/IJavetUniIndexedConsumer.java b/src/main/java/com/caoccao/javet/interfaces/IJavetUniIndexedConsumer.java index ddaedddfa..7f453d763 100644 --- a/src/main/java/com/caoccao/javet/interfaces/IJavetUniIndexedConsumer.java +++ b/src/main/java/com/caoccao/javet/interfaces/IJavetUniIndexedConsumer.java @@ -26,6 +26,7 @@ * @param the type parameter for custom exception * @since 0.8.10 */ +@FunctionalInterface public interface IJavetUniIndexedConsumer { /** * Accept. diff --git a/src/main/java/com/caoccao/javet/interop/IV8Native.java b/src/main/java/com/caoccao/javet/interop/IV8Native.java index 5775d5fcb..78fdcdf23 100644 --- a/src/main/java/com/caoccao/javet/interop/IV8Native.java +++ b/src/main/java/com/caoccao/javet/interop/IV8Native.java @@ -16,6 +16,8 @@ package com.caoccao.javet.interop; +import java.nio.ByteBuffer; + /** * The interface V8 native. * @@ -23,17 +25,25 @@ */ public interface IV8Native { - void add(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); - void allowCodeGenerationFromStrings(long v8RuntimeHandle, boolean allow); + Object arrayBufferCreate(long v8RuntimeHandle, int length); + + Object arrayBufferCreate(long v8RuntimeHandle, ByteBuffer byteBuffer); + + Object arrayCreate(long v8RuntimeHandle); + + int arrayGetLength(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + boolean await(long v8RuntimeHandle, int v8AwaitMode); - Object call( + int batchArrayGet( long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, - Object receiver, boolean returnResult, Object[] values); + Object[] v8Values, int startIndex, int endIndex); - Object callAsConstructor(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object[] values); + int batchObjectGet( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, + Object[] v8ValueKeys, Object[] v8ValueValues, int length); void clearInternalStatistic(); @@ -43,17 +53,6 @@ Object call( void closeV8Runtime(long v8RuntimeHandle); - Object compile( - long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, - String resourceName, int resourceLineOffset, int resourceColumnOffset, - int scriptId, boolean isWASM, boolean isModule); - - Object compileFunction( - long v8RuntimeHandle, String script, byte[] cachedData, - String resourceName, int resourceLineOffset, int resourceColumnOffset, - int scriptId, boolean wasm, - String[] arguments, Object[] contextExtensions); - Object contextGet(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, int index); int contextGetLength(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @@ -66,32 +65,43 @@ Object compileFunction( long createV8Runtime(Object runtimeOptions); - Object createV8Value(long v8RuntimeHandle, int v8ValueType, Object context); + boolean equals(long v8RuntimeHandle, long v8ValueHandle1, long v8ValueHandle2); - boolean delete(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + Object functionCall( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, + Object receiver, boolean returnResult, Object[] values); - boolean deletePrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String key); + Object functionCallAsConstructor(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object[] values); - boolean equals(long v8RuntimeHandle, long v8ValueHandle1, long v8ValueHandle2); + boolean functionCanDiscardCompiled(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); - Object execute( - long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + Object functionCompile( + long v8RuntimeHandle, String script, byte[] cachedData, String resourceName, int resourceLineOffset, int resourceColumnOffset, - int scriptId, boolean isWASM, boolean isModule); - - boolean functionCanDiscardCompiled(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + int scriptId, boolean wasm, + String[] arguments, Object[] contextExtensions); boolean functionCopyScopeInfoFrom( long v8RuntimeHandle, long targetV8ValueHandle, int targetV8ValueType, long sourceV8ValueHandle, int sourceV8ValueType); + Object functionCreate(long v8RuntimeHandle, Object callbackContext); + boolean functionDiscardCompiled(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); String[] functionGetArguments(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + byte[] functionGetCachedData(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + Object functionGetContext(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + Object functionGetInternalProperties(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + int functionGetJSFunctionType(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + int functionGetJSScopeType(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + Object functionGetScopeInfos( long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, boolean includeGlobalVariables, boolean includeScopeTypeGlobal); @@ -112,76 +122,88 @@ boolean functionSetScriptSource( boolean functionSetSourceCode( long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String sourceCode, boolean cloneScript); - Object get(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + Object getGlobalObject(long v8RuntimeHandle); - byte[] getCachedData(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + long[] getInternalStatistic(); - Object getGlobalObject(long v8RuntimeHandle); + Object getV8HeapSpaceStatistics(long v8RuntimeHandle, int allocationSpace); - int getIdentityHash(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + Object getV8HeapStatistics(long v8RuntimeHandle); - Object getInternalProperties(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + Object getV8SharedMemoryStatistics(); - long[] getInternalStatistic(); + String getVersion(); - int getJSFunctionType(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + boolean hasInternalType(long v8RuntimeHandle, long v8ValueHandle, int internalTypeId); - int getJSScopeType(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + boolean hasPendingException(long v8RuntimeHandle); - int getLength(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + boolean hasPendingMessage(long v8RuntimeHandle); - Object getOwnPropertyNames(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + boolean hasScheduledException(long v8RuntimeHandle); - Object getPrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String propertyName); + void idleNotificationDeadline(long v8RuntimeHandle, long deadlineInMillis); - Object getProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + boolean isDead(long v8RuntimeHandle); - Object getPropertyNames(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + boolean isInUse(long v8RuntimeHandle); - Object getPrototype(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + boolean isWeak(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); - int getSize(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + boolean lockV8Runtime(long v8RuntimeHandle); - Object getV8HeapSpaceStatistics(long v8RuntimeHandle, int allocationSpace); + void lowMemoryNotification(long v8RuntimeHandle); - Object getV8HeapStatistics(long v8RuntimeHandle); + Object mapCreate(long v8RuntimeHandle); - Object getV8SharedMemoryStatistics(); + boolean mapDelete(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); - String getVersion(); + Object mapGet(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); - boolean has(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); + boolean mapGetBoolean(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); - boolean hasInternalType(long v8RuntimeHandle, long v8ValueHandle, int internalTypeId); + double mapGetDouble(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); - boolean hasOwnProperty(long v8RuntimeHandle, long v8ValueHandle, int type, Object key); + int mapGetInteger(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); - boolean hasPendingException(long v8RuntimeHandle); + long mapGetLong(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); - boolean hasPendingMessage(long v8RuntimeHandle); + int mapGetSize(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); - boolean hasPrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int type, String propertyName); + String mapGetString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); - boolean hasScheduledException(long v8RuntimeHandle); + boolean mapHas(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); - void idleNotificationDeadline(long v8RuntimeHandle, long deadlineInMillis); + boolean mapSet(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object[] keysAndValues); - Object invoke( - long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, - String functionName, boolean returnResult, Object[] values); + boolean mapSetBoolean(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean value); - boolean isDead(long v8RuntimeHandle); + boolean mapSetDouble(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, double value); - boolean isInUse(long v8RuntimeHandle); + boolean mapSetInteger(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, int value); - boolean isWeak(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + boolean mapSetLong(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, long value); - boolean lockV8Runtime(long v8RuntimeHandle); + boolean mapSetNull(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); - void lowMemoryNotification(long v8RuntimeHandle); + boolean mapSetString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, String value); + + boolean mapSetUndefined(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + Object moduleCompile( + long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + String resourceName, int resourceLineOffset, int resourceColumnOffset, + int scriptId, boolean isWASM, boolean isModule); Object moduleEvaluate(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, boolean resultRequired); + Object moduleExecute( + long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + String resourceName, int resourceLineOffset, int resourceColumnOffset, + int scriptId, boolean isWASM); + + byte[] moduleGetCachedData(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + Object moduleGetException(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); Object moduleGetNamespace(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @@ -192,8 +214,78 @@ Object invoke( boolean moduleInstantiate(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + Object objectCreate(long v8RuntimeHandle); + + boolean objectDelete(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + boolean objectDeletePrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String key); + + Object objectGet(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + boolean objectGetBoolean(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); + + double objectGetDouble(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); + + int objectGetIdentityHash(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + int objectGetInteger(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); + + long objectGetLong(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); + + Object objectGetOwnPropertyNames(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + Object objectGetPrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String propertyName); + + Object objectGetProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + Object objectGetPropertyNames(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + Object objectGetPrototype(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + String objectGetString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + boolean objectHas(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); + + boolean objectHasOwnProperty(long v8RuntimeHandle, long v8ValueHandle, int type, Object key); + + boolean objectHasPrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int type, String propertyName); + + Object objectInvoke( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, + String functionName, boolean returnResult, Object[] values); + + boolean objectSet(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object[] keysAndValues); + + boolean objectSetAccessor( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, + Object propertyName, Object getter, Object setter); + + boolean objectSetBoolean(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean value); + + boolean objectSetDouble(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, double value); + + boolean objectSetInteger(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, int value); + + boolean objectSetLong(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, long value); + + boolean objectSetNull(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + boolean objectSetPrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String key, Object value); + + boolean objectSetProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, Object value); + + boolean objectSetPrototype(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, long v8ValueHandlePrototype); + + boolean objectSetString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, String value); + + boolean objectSetUndefined(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + String objectToProtoString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + Object promiseCatch(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, long v8ValueFunctionHandle); + Object promiseCreate(long v8RuntimeHandle); + Object promiseGetPromise(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); Object promiseGetResult(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @@ -214,6 +306,8 @@ Object promiseThen( boolean promoteScheduledException(long v8RuntimeHandle); + Object proxyCreate(long v8RuntimeHandle, Object target); + Object proxyGetHandler(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); Object proxyGetTarget(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @@ -242,27 +336,37 @@ Object promiseThen( boolean sameValue(long v8RuntimeHandle, long v8ValueHandle1, long v8ValueHandle2); + Object scriptCompile( + long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + String resourceName, int resourceLineOffset, int resourceColumnOffset, + int scriptId, boolean isWASM, boolean isModule); + + Object scriptExecute( + long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + String resourceName, int resourceLineOffset, int resourceColumnOffset, + int scriptId, boolean isWASM); + + byte[] scriptGetCachedData(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + Object scriptRun(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, boolean resultRequired); - boolean set(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, Object value); + void setAdd(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); - boolean setAccessor( - long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, - Object propertyName, Object getter, Object setter); + Object setCreate(long v8RuntimeHandle); - boolean setPrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String key, Object value); + boolean setDelete(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); - boolean setProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, Object value); + int setGetSize(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); - boolean setPrototype(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, long v8ValueHandlePrototype); + boolean setHas(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); void setWeak(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object objectReference); boolean strictEquals(long v8RuntimeHandle, long v8ValueHandle1, long v8ValueHandle2); - void terminateExecution(long v8RuntimeHandle); + Object symbolCreate(long v8RuntimeHandle, String description); - String toProtoString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + void terminateExecution(long v8RuntimeHandle); String toString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); diff --git a/src/main/java/com/caoccao/javet/interop/V8Internal.java b/src/main/java/com/caoccao/javet/interop/V8Internal.java index 76cbebaca..c58293b3d 100644 --- a/src/main/java/com/caoccao/javet/interop/V8Internal.java +++ b/src/main/java/com/caoccao/javet/interop/V8Internal.java @@ -34,25 +34,28 @@ public final class V8Internal { this.v8Runtime = Objects.requireNonNull(v8Runtime); } - public void add(IV8ValueSet iV8ValueKeySet, V8Value value) throws JavetException { - v8Runtime.add(iV8ValueKeySet, value); - } - public void addReference(IV8ValueReference iV8ValueReference) { v8Runtime.addReference(iV8ValueReference); } - @CheckReturnValue - public T call( - IV8ValueObject iV8ValueObject, IV8ValueObject receiver, boolean returnResult, V8Value... v8Values) + public int arrayGetLength(IV8ValueArray iV8ValueArray) throws JavetException { + return v8Runtime.arrayGetLength(iV8ValueArray); + } + + public int arrayGetLength(IV8ValueTypedArray iV8ValueTypedArray) throws JavetException { + return v8Runtime.arrayGetLength(iV8ValueTypedArray); + } + + public int batchArrayGet( + IV8ValueArray iV8ValueArray, V8Value[] v8Values, int startIndex, int endIndex) throws JavetException { - return v8Runtime.call(iV8ValueObject, receiver, returnResult, v8Values); + return v8Runtime.batchArrayGet(iV8ValueArray, v8Values, startIndex, endIndex); } - @CheckReturnValue - public T callAsConstructor( - IV8ValueObject iV8ValueObject, V8Value... v8Values) throws JavetException { - return v8Runtime.callAsConstructor(iV8ValueObject, v8Values); + public int batchObjectGet( + IV8ValueObject iV8ValueObject, V8Value[] v8ValueKeys, V8Value[] v8ValueValues, int length) + throws JavetException { + return v8Runtime.batchObjectGet(iV8ValueObject, v8ValueKeys, v8ValueValues, length); } public void clearWeak(IV8ValueReference iV8ValueReference) throws JavetException { @@ -83,17 +86,22 @@ public boolean contextSetLength(IV8Context iV8Context, int length) throws JavetE return v8Runtime.contextSetLength(iV8Context, length); } - public boolean delete(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { - return v8Runtime.delete(iV8ValueObject, key); + public boolean equals(IV8ValueReference iV8ValueReference1, IV8ValueReference iV8ValueReference2) + throws JavetException { + return v8Runtime.equals(iV8ValueReference1, iV8ValueReference2); } - public boolean deletePrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) throws JavetException { - return v8Runtime.deletePrivateProperty(iV8ValueObject, propertyName); + @CheckReturnValue + public T functionCall( + IV8ValueObject iV8ValueObject, IV8ValueObject receiver, boolean returnResult, V8Value... v8Values) + throws JavetException { + return v8Runtime.functionCall(iV8ValueObject, receiver, returnResult, v8Values); } - public boolean equals(IV8ValueReference iV8ValueReference1, IV8ValueReference iV8ValueReference2) - throws JavetException { - return v8Runtime.equals(iV8ValueReference1, iV8ValueReference2); + @CheckReturnValue + public T functionCallAsConstructor( + IV8ValueObject iV8ValueObject, V8Value... v8Values) throws JavetException { + return v8Runtime.functionCallAsConstructor(iV8ValueObject, v8Values); } public boolean functionCanDiscardCompiled(IV8ValueFunction iV8ValueFunction) { @@ -114,11 +122,28 @@ public String[] functionGetArguments(IV8ValueFunction iV8ValueFunction) throws J return v8Runtime.functionGetArguments(iV8ValueFunction); } + public byte[] functionGetCachedData(IV8ValueFunction iV8ValueFunction) throws JavetException { + return v8Runtime.functionGetCachedData(iV8ValueFunction); + } + @CheckReturnValue public V8Context functionGetContext(IV8ValueFunction iV8ValueFunction) throws JavetException { return v8Runtime.functionGetContext(iV8ValueFunction); } + @CheckReturnValue + public IV8ValueArray functionGetInternalProperties(IV8ValueFunction iV8ValueFunction) throws JavetException { + return v8Runtime.functionGetInternalProperties(iV8ValueFunction); + } + + public JSFunctionType functionGetJSFunctionType(IV8ValueFunction iV8ValueFunction) { + return v8Runtime.functionGetJSFunctionType(iV8ValueFunction); + } + + public JSScopeType functionGetJSScopeType(IV8ValueFunction iV8ValueFunction) { + return v8Runtime.functionGetJSScopeType(iV8ValueFunction); + } + @CheckReturnValue public IV8ValueArray functionGetScopeInfos( IV8ValueFunction iV8ValueFunction, @@ -160,104 +185,101 @@ public boolean functionSetSourceCode( return v8Runtime.functionSetSourceCode(iV8ValueFunction, sourceCode, cloneScript); } - @CheckReturnValue - public T get(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { - return v8Runtime.get(iV8ValueObject, key); - } - - public byte[] getCachedData(IV8ValueFunction iV8ValueFunction) throws JavetException { - return v8Runtime.getCachedData(iV8ValueFunction); - } - - public byte[] getCachedData(IV8Module iV8Module) throws JavetException { - return v8Runtime.getCachedData(iV8Module); + public boolean hasInternalType(IV8ValueObject iV8ValueObject, V8ValueInternalType internalType) { + return v8Runtime.hasInternalType(iV8ValueObject, internalType); } - public byte[] getCachedData(IV8Script iV8Script) throws JavetException { - return v8Runtime.getCachedData(iV8Script); + public boolean isWeak(IV8ValueReference iV8ValueReference) { + return v8Runtime.isWeak(iV8ValueReference); } - public int getIdentityHash(IV8ValueReference iV8ValueReference) throws JavetException { - return v8Runtime.getIdentityHash(iV8ValueReference); + public boolean mapDelete(IV8ValueMap iV8ValueMap, V8Value key) throws JavetException { + return v8Runtime.mapDelete(iV8ValueMap, key); } @CheckReturnValue - public IV8ValueArray getInternalProperties(IV8ValueFunction iV8ValueFunction) throws JavetException { - return v8Runtime.getInternalProperties(iV8ValueFunction); + public T mapGet(IV8ValueMap iV8ValueMap, V8Value key) throws JavetException { + return v8Runtime.mapGet(iV8ValueMap, key); } - public JSFunctionType getJSFunctionType(IV8ValueFunction iV8ValueFunction) { - return v8Runtime.getJSFunctionType(iV8ValueFunction); + public Boolean mapGetBoolean( + IV8ValueMap iV8ValueMap, V8Value key) + throws JavetException { + return v8Runtime.mapGetBoolean(iV8ValueMap, key); } - public JSScopeType getJSScopeType(IV8ValueFunction iV8ValueFunction) { - return v8Runtime.getJSScopeType(iV8ValueFunction); + public Double mapGetDouble( + IV8ValueMap iV8ValueMap, V8Value key) + throws JavetException { + return v8Runtime.mapGetDouble(iV8ValueMap, key); } - public int getLength(IV8ValueArray iV8ValueArray) throws JavetException { - return v8Runtime.getLength(iV8ValueArray); + public Integer mapGetInteger( + IV8ValueMap iV8ValueMap, V8Value key) + throws JavetException { + return v8Runtime.mapGetInteger(iV8ValueMap, key); } - public int getLength(IV8ValueTypedArray iV8ValueTypedArray) throws JavetException { - return v8Runtime.getLength(iV8ValueTypedArray); + public Long mapGetLong( + IV8ValueMap iV8ValueMap, V8Value key) + throws JavetException { + return v8Runtime.mapGetLong(iV8ValueMap, key); } - @CheckReturnValue - public IV8ValueArray getOwnPropertyNames( - IV8ValueObject iV8ValueObject) throws JavetException { - return v8Runtime.getOwnPropertyNames(iV8ValueObject); + public int mapGetSize(IV8ValueMap iV8ValueMap) throws JavetException { + return v8Runtime.mapGetSize(iV8ValueMap); } - @CheckReturnValue - public T getPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) + public String mapGetString( + IV8ValueMap iV8ValueMap, V8Value key) throws JavetException { - return v8Runtime.getPrivateProperty(iV8ValueObject, propertyName); + return v8Runtime.mapGetString(iV8ValueMap, key); } - @CheckReturnValue - public T getProperty(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { - return v8Runtime.getProperty(iV8ValueObject, key); + public boolean mapHas(IV8ValueMap iV8ValueMap, V8Value value) throws JavetException { + return v8Runtime.mapHas(iV8ValueMap, value); } - @CheckReturnValue - public IV8ValueArray getPropertyNames(IV8ValueObject iV8ValueObject) throws JavetException { - return v8Runtime.getPropertyNames(iV8ValueObject); + public boolean mapSet(IV8ValueMap iV8ValueMap, V8Value... v8Values) throws JavetException { + return v8Runtime.mapSet(iV8ValueMap, v8Values); } - @CheckReturnValue - public T getPrototype(IV8ValueObject iV8ValueObject) throws JavetException { - return v8Runtime.getPrototype(iV8ValueObject); - } - - public int getSize(IV8ValueKeyContainer iV8ValueKeyContainer) throws JavetException { - return v8Runtime.getSize(iV8ValueKeyContainer); + public boolean mapSetBoolean( + IV8ValueMap iV8ValueMap, V8Value key, boolean value) + throws JavetException { + return v8Runtime.mapSetBoolean(iV8ValueMap, key, value); } - public boolean has(IV8ValueObject iV8ValueObject, V8Value value) throws JavetException { - return v8Runtime.has(iV8ValueObject, value); + public boolean mapSetDouble( + IV8ValueMap iV8ValueMap, V8Value key, double value) + throws JavetException { + return v8Runtime.mapSetDouble(iV8ValueMap, key, value); } - public boolean hasInternalType(IV8ValueObject iV8ValueObject, V8ValueInternalType internalType) { - return v8Runtime.hasInternalType(iV8ValueObject, internalType); + public boolean mapSetInteger( + IV8ValueMap iV8ValueMap, V8Value key, int value) + throws JavetException { + return v8Runtime.mapSetInteger(iV8ValueMap, key, value); } - public boolean hasOwnProperty(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { - return v8Runtime.hasOwnProperty(iV8ValueObject, key); + public boolean mapSetLong( + IV8ValueMap iV8ValueMap, V8Value key, long value) + throws JavetException { + return v8Runtime.mapSetLong(iV8ValueMap, key, value); } - public boolean hasPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) throws JavetException { - return v8Runtime.hasPrivateProperty(iV8ValueObject, propertyName); + public boolean mapSetNull(IV8ValueMap iV8ValueMap, V8Value key) throws JavetException { + return v8Runtime.mapSetNull(iV8ValueMap, key); } - @CheckReturnValue - public T invoke( - IV8ValueObject iV8ValueObject, String functionName, boolean returnResult, V8Value... v8Values) + public boolean mapSetString( + IV8ValueMap iV8ValueMap, V8Value key, String value) throws JavetException { - return v8Runtime.invoke(iV8ValueObject, functionName, returnResult, v8Values); + return v8Runtime.mapSetString(iV8ValueMap, key, value); } - public boolean isWeak(IV8ValueReference iV8ValueReference) { - return v8Runtime.isWeak(iV8ValueReference); + public boolean mapSetUndefined(IV8ValueMap iV8ValueMap, V8Value key) throws JavetException { + return v8Runtime.mapSetUndefined(iV8ValueMap, key); } @CheckReturnValue @@ -266,6 +288,10 @@ public T moduleEvaluate( return v8Runtime.moduleEvaluate(iV8Module, resultRequired); } + public byte[] moduleGetCachedData(IV8Module iV8Module) throws JavetException { + return v8Runtime.moduleGetCachedData(iV8Module); + } + @CheckReturnValue public V8ValueError moduleGetException(IV8Module iV8Module) throws JavetException { return v8Runtime.moduleGetException(iV8Module); @@ -288,6 +314,172 @@ public boolean moduleInstantiate(IV8Module iV8Module) throws JavetException { return v8Runtime.moduleInstantiate(iV8Module); } + public boolean objectDelete(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Runtime.objectDelete(iV8ValueObject, key); + } + + public boolean objectDeletePrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) throws JavetException { + return v8Runtime.objectDeletePrivateProperty(iV8ValueObject, propertyName); + } + + @CheckReturnValue + public T objectGet(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Runtime.objectGet(iV8ValueObject, key); + } + + public Boolean objectGetBoolean( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + return v8Runtime.objectGetBoolean(iV8ValueObject, key); + } + + public Double objectGetDouble( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + return v8Runtime.objectGetDouble(iV8ValueObject, key); + } + + public int objectGetIdentityHash(IV8ValueReference iV8ValueReference) throws JavetException { + return v8Runtime.objectGetIdentityHash(iV8ValueReference); + } + + public Integer objectGetInteger( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + return v8Runtime.objectGetInteger(iV8ValueObject, key); + } + + public Long objectGetLong( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + return v8Runtime.objectGetLong(iV8ValueObject, key); + } + + @CheckReturnValue + public IV8ValueArray objectGetOwnPropertyNames( + IV8ValueObject iV8ValueObject) throws JavetException { + return v8Runtime.objectGetOwnPropertyNames(iV8ValueObject); + } + + @CheckReturnValue + public T objectGetPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) + throws JavetException { + return v8Runtime.objectGetPrivateProperty(iV8ValueObject, propertyName); + } + + @CheckReturnValue + public T objectGetProperty(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Runtime.objectGetProperty(iV8ValueObject, key); + } + + @CheckReturnValue + public IV8ValueArray objectGetPropertyNames(IV8ValueObject iV8ValueObject) throws JavetException { + return v8Runtime.objectGetPropertyNames(iV8ValueObject); + } + + @CheckReturnValue + public T objectGetPrototype(IV8ValueObject iV8ValueObject) throws JavetException { + return v8Runtime.objectGetPrototype(iV8ValueObject); + } + + public String objectGetString( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + return v8Runtime.objectGetString(iV8ValueObject, key); + } + + public boolean objectHas(IV8ValueObject iV8ValueObject, V8Value value) throws JavetException { + return v8Runtime.objectHas(iV8ValueObject, value); + } + + public boolean objectHasOwnProperty(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Runtime.objectHasOwnProperty(iV8ValueObject, key); + } + + public boolean objectHasPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) throws JavetException { + return v8Runtime.objectHasPrivateProperty(iV8ValueObject, propertyName); + } + + @CheckReturnValue + public T objectInvoke( + IV8ValueObject iV8ValueObject, String functionName, boolean returnResult, V8Value... v8Values) + throws JavetException { + return v8Runtime.objectInvoke(iV8ValueObject, functionName, returnResult, v8Values); + } + + public boolean objectSet(IV8ValueObject iV8ValueObject, V8Value... v8Values) throws JavetException { + return v8Runtime.objectSet(iV8ValueObject, v8Values); + } + + public boolean objectSetAccessor( + IV8ValueObject iV8ValueObject, + V8Value propertyName, + JavetCallbackContext javetCallbackContextGetter, + JavetCallbackContext javetCallbackContextSetter) throws JavetException { + return v8Runtime.objectSetAccessor( + iV8ValueObject, propertyName, javetCallbackContextGetter, javetCallbackContextSetter); + } + + public boolean objectSetBoolean( + IV8ValueObject iV8ValueObject, V8Value key, boolean value) + throws JavetException { + return v8Runtime.objectSetBoolean(iV8ValueObject, key, value); + } + + public boolean objectSetDouble( + IV8ValueObject iV8ValueObject, V8Value key, double value) + throws JavetException { + return v8Runtime.objectSetDouble(iV8ValueObject, key, value); + } + + public boolean objectSetInteger( + IV8ValueObject iV8ValueObject, V8Value key, int value) + throws JavetException { + return v8Runtime.objectSetInteger(iV8ValueObject, key, value); + } + + public boolean objectSetLong( + IV8ValueObject iV8ValueObject, V8Value key, long value) + throws JavetException { + return v8Runtime.objectSetLong(iV8ValueObject, key, value); + } + + public boolean objectSetNull(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Runtime.objectSetNull(iV8ValueObject, key); + } + + public boolean objectSetPrivateProperty( + IV8ValueObject iV8ValueObject, String propertyName, V8Value propertyValue) + throws JavetException { + return v8Runtime.objectSetPrivateProperty(iV8ValueObject, propertyName, propertyValue); + } + + public boolean objectSetProperty( + IV8ValueObject iV8ValueObject, V8Value key, V8Value value) + throws JavetException { + return v8Runtime.objectSetProperty(iV8ValueObject, key, value); + } + + public boolean objectSetPrototype( + IV8ValueObject iV8ValueObject, IV8ValueObject iV8ValueObjectPrototype) + throws JavetException { + return v8Runtime.objectSetPrototype(iV8ValueObject, iV8ValueObjectPrototype); + } + + public boolean objectSetString( + IV8ValueObject iV8ValueObject, V8Value key, String value) + throws JavetException { + return v8Runtime.objectSetString(iV8ValueObject, key, value); + } + + public boolean objectSetUndefined(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Runtime.objectSetUndefined(iV8ValueObject, key); + } + + public String objectToProtoString(IV8ValueReference iV8ValueReference) throws JavetException { + return v8Runtime.objectToProtoString(iV8ValueReference); + } + public T promiseCatch( IV8ValuePromise iV8ValuePromise, IV8ValueFunction functionHandle) throws JavetException { return v8Runtime.promiseCatch(iV8ValuePromise, functionHandle); @@ -354,36 +546,29 @@ public boolean sameValue(IV8ValueObject iV8ValueObject1, IV8ValueObject iV8Value return v8Runtime.sameValue(iV8ValueObject1, iV8ValueObject2); } + public byte[] scriptGetCachedData(IV8Script iV8Script) throws JavetException { + return v8Runtime.scriptGetCachedData(iV8Script); + } + public T scriptRun( IV8Script iV8Script, boolean resultRequired) throws JavetException { return v8Runtime.scriptRun(iV8Script, resultRequired); } - public boolean set(IV8ValueObject iV8ValueObject, V8Value key, V8Value value) throws JavetException { - return v8Runtime.set(iV8ValueObject, key, value); + public void setAdd(IV8ValueSet iV8ValueKeySet, V8Value value) throws JavetException { + v8Runtime.setAdd(iV8ValueKeySet, value); } - public boolean setAccessor( - IV8ValueObject iV8ValueObject, - V8Value propertyName, - JavetCallbackContext javetCallbackContextGetter, - JavetCallbackContext javetCallbackContextSetter) throws JavetException { - return v8Runtime.setAccessor( - iV8ValueObject, propertyName, javetCallbackContextGetter, javetCallbackContextSetter); + public boolean setDelete(IV8ValueSet iV8ValueSet, V8Value key) throws JavetException { + return v8Runtime.setDelete(iV8ValueSet, key); } - public boolean setPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName, V8Value propertyValue) - throws JavetException { - return v8Runtime.setPrivateProperty(iV8ValueObject, propertyName, propertyValue); - } - - public boolean setProperty(IV8ValueObject iV8ValueObject, V8Value key, V8Value value) throws JavetException { - return v8Runtime.setProperty(iV8ValueObject, key, value); + public int setGetSize(IV8ValueSet iV8ValueKeySet) throws JavetException { + return v8Runtime.setGetSize(iV8ValueKeySet); } - public boolean setPrototype( - IV8ValueObject iV8ValueObject, IV8ValueObject iV8ValueObjectPrototype) throws JavetException { - return v8Runtime.setPrototype(iV8ValueObject, iV8ValueObjectPrototype); + public boolean setHas(IV8ValueSet iV8ValueSet, V8Value value) throws JavetException { + return v8Runtime.setHas(iV8ValueSet, value); } public void setWeak(IV8ValueReference iV8ValueReference) { @@ -394,10 +579,6 @@ public boolean strictEquals(IV8ValueObject iV8ValueObject1, IV8ValueObject iV8Va return v8Runtime.strictEquals(iV8ValueObject1, iV8ValueObject2); } - public String toProtoString(IV8ValueReference iV8ValueReference) throws JavetException { - return v8Runtime.toProtoString(iV8ValueReference); - } - public String toString(IV8ValueReference iV8ValueReference) throws JavetException { return v8Runtime.toString(iV8ValueReference); } diff --git a/src/main/java/com/caoccao/javet/interop/V8Native.java b/src/main/java/com/caoccao/javet/interop/V8Native.java index 89a4e4511..82704cbcf 100644 --- a/src/main/java/com/caoccao/javet/interop/V8Native.java +++ b/src/main/java/com/caoccao/javet/interop/V8Native.java @@ -16,6 +16,8 @@ package com.caoccao.javet.interop; +import java.nio.ByteBuffer; + /** * The type V8 public native is the pure interface that defines the JNI C++ implementation. * It has to be public so that dynamic library loading can work. @@ -33,22 +35,32 @@ class V8Native implements IV8Native { } @Override - public native void add(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); + public native void allowCodeGenerationFromStrings(long v8RuntimeHandle, boolean allow); @Override - public native void allowCodeGenerationFromStrings(long v8RuntimeHandle, boolean allow); + public native Object arrayBufferCreate(long v8RuntimeHandle, int length); + + @Override + public native Object arrayBufferCreate(long v8RuntimeHandle, ByteBuffer byteBuffer); + + @Override + public native Object arrayCreate(long v8RuntimeHandle); + + @Override + public native int arrayGetLength(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @Override public native boolean await(long v8RuntimeHandle, int v8AwaitMode); @Override - public native Object call( + public native int batchArrayGet( long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, - Object receiver, boolean returnResult, Object[] values); + Object[] v8Values, int startIndex, int endIndex); @Override - public native Object callAsConstructor( - long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object[] values); + public native int batchObjectGet( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, + Object[] v8ValueKeys, Object[] v8ValueValues, int length); @Override public native void clearInternalStatistic(); @@ -63,19 +75,6 @@ public native Object cloneV8Value( @Override public native void closeV8Runtime(long v8RuntimeHandle); - @Override - public native Object compile( - long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, - String resourceName, int resourceLineOffset, int resourceColumnOffset, - int scriptId, boolean isWASM, boolean isModule); - - @Override - public native Object compileFunction( - long v8RuntimeHandle, String script, byte[] cachedData, - String resourceName, int resourceLineOffset, int resourceColumnOffset, - int scriptId, boolean wasm, - String[] arguments, Object[] contextExtensions); - @Override public native Object contextGet(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, int index); @@ -95,25 +94,26 @@ public native Object compileFunction( public native long createV8Runtime(Object runtimeOptions); @Override - public native Object createV8Value(long v8RuntimeHandle, int v8ValueType, Object context); + public native boolean equals(long v8RuntimeHandle, long v8ValueHandle1, long v8ValueHandle2); @Override - public native boolean delete(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + public native Object functionCall( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, + Object receiver, boolean returnResult, Object[] values); @Override - public native boolean deletePrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String key); + public native Object functionCallAsConstructor( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object[] values); @Override - public native boolean equals(long v8RuntimeHandle, long v8ValueHandle1, long v8ValueHandle2); + public native boolean functionCanDiscardCompiled(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @Override - public native Object execute( - long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + public native Object functionCompile( + long v8RuntimeHandle, String script, byte[] cachedData, String resourceName, int resourceLineOffset, int resourceColumnOffset, - int scriptId, boolean isWASM, boolean isModule); - - @Override - public native boolean functionCanDiscardCompiled(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + int scriptId, boolean wasm, + String[] arguments, Object[] contextExtensions); @Override public native boolean functionCopyScopeInfoFrom( @@ -121,15 +121,30 @@ public native boolean functionCopyScopeInfoFrom( long targetV8ValueHandle, int targetV8ValueType, long sourceV8ValueHandle, int sourceV8ValueType); + @Override + public native Object functionCreate(long v8RuntimeHandle, Object callbackContext); + @Override public native boolean functionDiscardCompiled(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @Override public native String[] functionGetArguments(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + @Override + public native byte[] functionGetCachedData(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + @Override public native Object functionGetContext(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + @Override + public native Object functionGetInternalProperties(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + @Override + public native int functionGetJSFunctionType(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + @Override + public native int functionGetJSScopeType(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + @Override public native Object functionGetScopeInfos( long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, @@ -159,110 +174,134 @@ public native boolean functionSetSourceCode( long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String sourceCode, boolean cloneScript); @Override - public native Object get(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + public native Object getGlobalObject(long v8RuntimeHandle); @Override - public native byte[] getCachedData(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native long[] getInternalStatistic(); @Override - public native Object getGlobalObject(long v8RuntimeHandle); + public native Object getV8HeapSpaceStatistics(long v8RuntimeHandle, int allocationSpace); @Override - public native int getIdentityHash(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native Object getV8HeapStatistics(long v8RuntimeHandle); @Override - public native Object getInternalProperties(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native Object getV8SharedMemoryStatistics(); @Override - public native long[] getInternalStatistic(); + public native String getVersion(); @Override - public native int getJSFunctionType(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native boolean hasInternalType(long v8RuntimeHandle, long v8ValueHandle, int internalTypeId); @Override - public native int getJSScopeType(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native boolean hasPendingException(long v8RuntimeHandle); @Override - public native int getLength(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native boolean hasPendingMessage(long v8RuntimeHandle); @Override - public native Object getOwnPropertyNames(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native boolean hasScheduledException(long v8RuntimeHandle); @Override - public native Object getPrivateProperty( - long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String propertyName); + public native void idleNotificationDeadline(long v8RuntimeHandle, long deadlineInMillis); @Override - public native Object getProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + public native boolean isDead(long v8RuntimeHandle); @Override - public native Object getPropertyNames(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native boolean isInUse(long v8RuntimeHandle); @Override - public native Object getPrototype(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native boolean isWeak(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @Override - public native int getSize(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native boolean lockV8Runtime(long v8RuntimeHandle); @Override - public native Object getV8HeapSpaceStatistics(long v8RuntimeHandle, int allocationSpace); + public native void lowMemoryNotification(long v8RuntimeHandle); @Override - public native Object getV8HeapStatistics(long v8RuntimeHandle); + public native Object mapCreate(long v8RuntimeHandle); @Override - public native Object getV8SharedMemoryStatistics(); + public native boolean mapDelete(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); @Override - public native String getVersion(); + public native Object mapGet(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); @Override - public native boolean has(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); + public native boolean mapGetBoolean( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); @Override - public native boolean hasInternalType(long v8RuntimeHandle, long v8ValueHandle, int internalTypeId); + public native double mapGetDouble( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); @Override - public native boolean hasOwnProperty(long v8RuntimeHandle, long v8ValueHandle, int type, Object key); + public native int mapGetInteger( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); @Override - public native boolean hasPendingException(long v8RuntimeHandle); + public native long mapGetLong( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); @Override - public native boolean hasPendingMessage(long v8RuntimeHandle); + public native int mapGetSize(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @Override - public native boolean hasPrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int type, String propertyName); + public native String mapGetString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); @Override - public native boolean hasScheduledException(long v8RuntimeHandle); + public native boolean mapHas(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); @Override - public native void idleNotificationDeadline(long v8RuntimeHandle, long deadlineInMillis); + public native boolean mapSet(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object[] keysAndValues); @Override - public native Object invoke( - long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, - String functionName, boolean returnResult, Object[] values); + public native boolean mapSetBoolean( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean value); @Override - public native boolean isDead(long v8RuntimeHandle); + public native boolean mapSetDouble( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, double value); @Override - public native boolean isInUse(long v8RuntimeHandle); + public native boolean mapSetInteger( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, int value); @Override - public native boolean isWeak(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native boolean mapSetLong( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, long value); @Override - public native boolean lockV8Runtime(long v8RuntimeHandle); + public native boolean mapSetNull(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); @Override - public native void lowMemoryNotification(long v8RuntimeHandle); + public native boolean mapSetString( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, String value); + + @Override + public native boolean mapSetUndefined(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + @Override + public native Object moduleCompile( + long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + String resourceName, int resourceLineOffset, int resourceColumnOffset, + int scriptId, boolean isWASM, boolean isModule); @Override public native Object moduleEvaluate(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, boolean resultRequired); + @Override + public native Object moduleExecute( + long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + String resourceName, int resourceLineOffset, int resourceColumnOffset, + int scriptId, boolean isWASM); + + @Override + public native byte[] moduleGetCachedData(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + @Override public native Object moduleGetException(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @@ -279,7 +318,126 @@ public native Object invoke( public native boolean moduleInstantiate(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @Override - public native Object promiseCatch(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, long v8ValueFunctionHandle); + public native Object objectCreate(long v8RuntimeHandle); + + @Override + public native boolean objectDelete(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + @Override + public native boolean objectDeletePrivateProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String key); + + @Override + public native Object objectGet(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + @Override + public native boolean objectGetBoolean( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); + + @Override + public native double objectGetDouble( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); + + @Override + public native int objectGetIdentityHash(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + @Override + public native int objectGetInteger( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); + + @Override + public native long objectGetLong( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean[] primitiveFlags); + + @Override + public native Object objectGetOwnPropertyNames(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + @Override + public native Object objectGetPrivateProperty( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String propertyName); + + @Override + public native Object objectGetProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + @Override + public native Object objectGetPropertyNames(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + @Override + public native Object objectGetPrototype(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + @Override + public native String objectGetString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + @Override + public native boolean objectHas(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); + + @Override + public native boolean objectHasOwnProperty(long v8RuntimeHandle, long v8ValueHandle, int type, Object key); + + @Override + public native boolean objectHasPrivateProperty( + long v8RuntimeHandle, long v8ValueHandle, int type, String propertyName); + + @Override + public native Object objectInvoke( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, + String functionName, boolean returnResult, Object[] values); + + @Override + public native boolean objectSet( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object[] keysAndValues); + + @Override + public native boolean objectSetAccessor( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, + Object propertyName, Object getter, Object setter); + + @Override + public native boolean objectSetBoolean( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, boolean value); + + @Override + public native boolean objectSetDouble( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, double value); + + @Override + public native boolean objectSetInteger( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, int value); + + @Override + public native boolean objectSetLong( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, long value); + + @Override + public native boolean objectSetNull(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + @Override + public native boolean objectSetPrivateProperty( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String key, Object value); + + @Override + public native boolean objectSetProperty( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, Object value); + + @Override + public native boolean objectSetPrototype( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, long v8ValueHandlePrototype); + + @Override + public native boolean objectSetString( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, String value); + + @Override + public native boolean objectSetUndefined(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); + + @Override + public native String objectToProtoString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + + @Override + public native Object promiseCatch( + long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, long v8ValueFunctionHandle); + + @Override + public native Object promiseCreate(long v8RuntimeHandle); @Override public native Object promiseGetPromise(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @@ -310,6 +468,9 @@ public native Object promiseThen( @Override public native boolean promoteScheduledException(long v8RuntimeHandle); + @Override + public native Object proxyCreate(long v8RuntimeHandle, Object target); + @Override public native Object proxyGetHandler(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @@ -352,26 +513,38 @@ public native Object promiseThen( @Override public native boolean sameValue(long v8RuntimeHandle, long v8ValueHandle1, long v8ValueHandle2); + @Override + public native Object scriptCompile( + long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + String resourceName, int resourceLineOffset, int resourceColumnOffset, + int scriptId, boolean isWASM, boolean isModule); + + @Override + public native Object scriptExecute( + long v8RuntimeHandle, String script, byte[] cachedData, boolean returnResult, + String resourceName, int resourceLineOffset, int resourceColumnOffset, + int scriptId, boolean isWASM); + + @Override + public native byte[] scriptGetCachedData(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + @Override public native Object scriptRun(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, boolean resultRequired); @Override - public native boolean set(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, Object value); + public native void setAdd(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); @Override - public native boolean setAccessor( - long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object propertyName, Object getter, Object setter); + public native Object setCreate(long v8RuntimeHandle); @Override - public native boolean setPrivateProperty( - long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, String key, Object value); + public native boolean setDelete(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key); @Override - public native boolean setProperty(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object key, Object value); + public native int setGetSize(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); @Override - public native boolean setPrototype( - long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, long v8ValueHandlePrototype); + public native boolean setHas(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object value); @Override public native void setWeak(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType, Object objectReference); @@ -380,10 +553,10 @@ public native boolean setPrototype( public native boolean strictEquals(long v8RuntimeHandle, long v8ValueHandle1, long v8ValueHandle2); @Override - public native void terminateExecution(long v8RuntimeHandle); + public native Object symbolCreate(long v8RuntimeHandle, String description); @Override - public native String toProtoString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); + public native void terminateExecution(long v8RuntimeHandle); @Override public native String toString(long v8RuntimeHandle, long v8ValueHandle, int v8ValueType); diff --git a/src/main/java/com/caoccao/javet/interop/V8Runtime.java b/src/main/java/com/caoccao/javet/interop/V8Runtime.java index cf4feccfe..7ca2d1eaf 100644 --- a/src/main/java/com/caoccao/javet/interop/V8Runtime.java +++ b/src/main/java/com/caoccao/javet/interop/V8Runtime.java @@ -70,6 +70,37 @@ */ @SuppressWarnings("unchecked") public class V8Runtime implements IJavetClosable, IV8Creatable, IV8Convertible { + /** + * The constant ERROR_BYTE_BUFFER_MUST_BE_DIRECT. + * + * @since 2.2.0 + */ + protected static final String ERROR_BYTE_BUFFER_MUST_BE_DIRECT = "Byte buffer must be direct."; + /** + * The constant ERROR_HANDLE_MUST_BE_VALID. + * + * @since 2.2.0 + */ + protected static final String ERROR_HANDLE_MUST_BE_VALID = "Handle must be valid."; + /** + * The constant ERROR_SYMBOL_DESCRIPTION_CANNOT_BE_EMPTY. + * + * @since 2.2.0 + */ + protected static final String ERROR_SYMBOL_DESCRIPTION_CANNOT_BE_EMPTY = "Symbol description cannot be empty."; + /** + * The constant ERROR_THE_KEY_VALUE_PAIR_MUST_MATCH. + * + * @since 2.2.0 + */ + protected static final String ERROR_THE_KEY_VALUE_PAIR_MUST_MATCH = "The key value pair must match."; + /** + * The constant ERROR_THE_PROPERTY_NAME_MUST_BE_EITHER_STRING_OR_SYMBOL. + * + * @since 2.2.0 + */ + protected static final String ERROR_THE_PROPERTY_NAME_MUST_BE_EITHER_STRING_OR_SYMBOL = + "The property name must be either string or symbol."; /** * The Default converter. * @@ -146,6 +177,13 @@ public class V8Runtime implements IJavetClosable, IV8Creatable, IV8Convertible { * @since 1.0.3 */ final List gcPrologueCallbacks; + /** + * The Primitive flags is for passing the calling succession in JNI calls. + * It's length is 1. True: success. False: failure. + * + * @since 2.2.0 + */ + final boolean[] primitiveFlags; /** * The Reference lock. * @@ -284,7 +322,7 @@ public class V8Runtime implements IJavetClosable, IV8Creatable, IV8Convertible { * @since 0.7.0 */ V8Runtime(V8Host v8Host, long handle, boolean pooled, IV8Native v8Native, RuntimeOptions runtimeOptions) { - assert handle != 0; + assert handle != INVALID_HANDLE : ERROR_HANDLE_MUST_BE_VALID; callbackContextLock = new Object(); callbackContextMap = new HashMap<>(); converter = DEFAULT_CONVERTER; @@ -295,6 +333,7 @@ public class V8Runtime implements IJavetClosable, IV8Creatable, IV8Convertible { this.handle = handle; logger = new JavetDefaultLogger(getClass().getName()); this.pooled = pooled; + primitiveFlags = new boolean[1]; promiseRejectCallback = new JavetPromiseRejectCallback(logger); referenceLock = new Object(); referenceMap = new HashMap<>(); @@ -308,19 +347,6 @@ public class V8Runtime implements IJavetClosable, IV8Creatable, IV8Convertible { initializeV8ValueCache(); } - /** - * Add a value to a set. - * - * @param iV8ValueSet the V8 value set - * @param value the value - * @throws JavetException the javet exception - * @since 0.7.0 - */ - @SuppressWarnings("RedundantThrows") - void add(IV8ValueSet iV8ValueSet, V8Value value) throws JavetException { - v8Native.add(handle, iV8ValueSet.getHandle(), iV8ValueSet.getType().getId(), value); - } - /** * Add GC epilogue callback. * @@ -387,6 +413,32 @@ public void allowEval(boolean allow) { v8Native.allowCodeGenerationFromStrings(handle, allow); } + /** + * Gets length from an array. + * + * @param iV8ValueArray the V8 value array + * @return the length + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + int arrayGetLength(IV8ValueArray iV8ValueArray) throws JavetException { + return v8Native.arrayGetLength(handle, iV8ValueArray.getHandle(), iV8ValueArray.getType().getId()); + } + + /** + * Gets length from a typed array. + * + * @param iV8ValueTypedArray the V8 value typed array + * @return the length + * @throws JavetException the javet exception + * @since 0.8.4 + */ + @SuppressWarnings("RedundantThrows") + int arrayGetLength(IV8ValueTypedArray iV8ValueTypedArray) throws JavetException { + return v8Native.arrayGetLength(handle, iV8ValueTypedArray.getHandle(), iV8ValueTypedArray.getType().getId()); + } + /** * Await tells the V8 runtime to pump the message loop in a non-blocking manner. * @@ -412,46 +464,43 @@ public boolean await(V8AwaitMode v8AwaitMode) { } /** - * Call a function. - *

    - * It is similar to JavaScript built-in functions apply() or call(). + * Get the given range of items from the array. * - * @param the type parameter - * @param iV8ValueObject the V8 value object - * @param receiver the receiver - * @param returnResult the return result - * @param v8Values the V8 values - * @return the result + * @param iV8ValueArray the V8 value array + * @param v8Values the V8 values + * @param startIndex the start index + * @param endIndex the end index + * @return the actual item count * @throws JavetException the javet exception - * @since 0.7.0 + * @since 2.2.0 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") - T call( - IV8ValueObject iV8ValueObject, IV8ValueObject receiver, boolean returnResult, - V8Value... v8Values) + public int batchArrayGet( + IV8ValueArray iV8ValueArray, V8Value[] v8Values, int startIndex, int endIndex) throws JavetException { - return (T) v8Native.call( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), - receiver, returnResult, v8Values); + return v8Native.batchArrayGet( + handle, iV8ValueArray.getHandle(), iV8ValueArray.getType().getId(), + v8Values, startIndex, endIndex); } /** - * Call a function as a constructor. + * Batch get a range of values by keys. * - * @param the type parameter * @param iV8ValueObject the V8 value object - * @param v8Values the V8 values - * @return the result + * @param v8ValueKeys the V8 value keys + * @param v8ValueValues the V8 value values + * @param length the length + * @return the actual item count * @throws JavetException the javet exception - * @since 0.7.2 + * @since 2.2.0 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") - T callAsConstructor( - IV8ValueObject iV8ValueObject, V8Value... v8Values) throws JavetException { - return (T) v8Native.callAsConstructor( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), v8Values); + public int batchObjectGet( + IV8ValueObject iV8ValueObject, V8Value[] v8ValueKeys, V8Value[] v8ValueValues, int length) + throws JavetException { + return v8Native.batchObjectGet( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), + v8ValueKeys, v8ValueValues, length); } /** @@ -476,8 +525,8 @@ void clearWeak(IV8ValueReference iV8ValueReference) throws JavetException { * @throws JavetException the javet exception * @since 0.7.0 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue T cloneV8Value( IV8ValueReference iV8ValueReference, boolean referenceCopy) @@ -526,7 +575,7 @@ public V8Module compileV8Module( if (v8ScriptOrigin.getResourceName() == null || v8ScriptOrigin.getResourceName().length() == 0) { throw new JavetException(JavetError.ModuleNameEmpty); } - Object result = v8Native.compile( + Object result = v8Native.moduleCompile( handle, scriptString, cachedData, resultRequired, v8ScriptOrigin.getResourceName(), v8ScriptOrigin.getResourceLineOffset(), v8ScriptOrigin.getResourceColumnOffset(), v8ScriptOrigin.getScriptId(), v8ScriptOrigin.isWasm(), v8ScriptOrigin.isModule()); @@ -556,7 +605,7 @@ public V8Script compileV8Script( String scriptString, byte[] cachedData, V8ScriptOrigin v8ScriptOrigin, boolean resultRequired) throws JavetException { v8ScriptOrigin.setModule(false); - return (V8Script) v8Native.compile( + return (V8Script) v8Native.scriptCompile( handle, scriptString, cachedData, resultRequired, v8ScriptOrigin.getResourceName(), v8ScriptOrigin.getResourceLineOffset(), v8ScriptOrigin.getResourceColumnOffset(), v8ScriptOrigin.getScriptId(), v8ScriptOrigin.isWasm(), v8ScriptOrigin.isModule()); @@ -580,7 +629,7 @@ public V8ValueFunction compileV8ValueFunction( String scriptString, byte[] cachedData, V8ScriptOrigin v8ScriptOrigin, String[] arguments, V8ValueObject[] contextExtensions) throws JavetException { - return (V8ValueFunction) v8Native.compileFunction( + return (V8ValueFunction) v8Native.functionCompile( handle, scriptString, cachedData, v8ScriptOrigin.getResourceName(), v8ScriptOrigin.getResourceLineOffset(), v8ScriptOrigin.getResourceColumnOffset(), v8ScriptOrigin.getScriptId(), v8ScriptOrigin.isWasm(), @@ -656,27 +705,26 @@ boolean contextSetLength(IV8Context iV8Context, int length) throws JavetExceptio } @Override + @SuppressWarnings("RedundantThrows") @CheckReturnValue public V8ValueArray createV8ValueArray() throws JavetException { - return (V8ValueArray) v8Native.createV8Value( - handle, V8ValueReferenceType.Array.getId(), null); + return (V8ValueArray) v8Native.arrayCreate(handle); } @Override + @SuppressWarnings("RedundantThrows") @CheckReturnValue public V8ValueArrayBuffer createV8ValueArrayBuffer(int length) throws JavetException { - return (V8ValueArrayBuffer) v8Native.createV8Value( - handle, V8ValueReferenceType.ArrayBuffer.getId(), createV8ValueInteger(length)); + return (V8ValueArrayBuffer) v8Native.arrayBufferCreate(handle, length); } @Override - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue public V8ValueArrayBuffer createV8ValueArrayBuffer(ByteBuffer byteBuffer) throws JavetException { Objects.requireNonNull(byteBuffer); - assert byteBuffer.isDirect() : "Byte buffer must be direct."; - return (V8ValueArrayBuffer) v8Native.createV8Value( - handle, V8ValueReferenceType.ArrayBuffer.getId(), byteBuffer); + assert byteBuffer.isDirect() : ERROR_BYTE_BUFFER_MUST_BE_DIRECT; + return (V8ValueArrayBuffer) v8Native.arrayBufferCreate(handle, byteBuffer); } @Override @@ -718,8 +766,8 @@ public V8ValueDouble createV8ValueDouble(double doubleValue) throws JavetExcepti @Override @CheckReturnValue public V8ValueFunction createV8ValueFunction(JavetCallbackContext javetCallbackContext) throws JavetException { - V8ValueFunction v8ValueFunction = (V8ValueFunction) v8Native.createV8Value( - handle, V8ValueReferenceType.Function.getId(), Objects.requireNonNull(javetCallbackContext)); + V8ValueFunction v8ValueFunction = (V8ValueFunction) v8Native.functionCreate( + handle, Objects.requireNonNull(javetCallbackContext)); synchronized (callbackContextLock) { callbackContextMap.put(javetCallbackContext.getHandle(), javetCallbackContext); } @@ -753,8 +801,7 @@ public V8ValueLong createV8ValueLong(long longValue) throws JavetException { @CheckReturnValue @SuppressWarnings("RedundantThrows") public V8ValueMap createV8ValueMap() throws JavetException { - return (V8ValueMap) v8Native.createV8Value( - handle, V8ValueReferenceType.Map.getId(), null); + return (V8ValueMap) v8Native.mapCreate(handle); } @Override @@ -763,34 +810,31 @@ public V8ValueNull createV8ValueNull() { } @Override + @SuppressWarnings("RedundantThrows") @CheckReturnValue public V8ValueObject createV8ValueObject() throws JavetException { - return (V8ValueObject) v8Native.createV8Value( - handle, V8ValueReferenceType.Object.getId(), null); + return (V8ValueObject) v8Native.objectCreate(handle); } @Override - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue public V8ValuePromise createV8ValuePromise() throws JavetException { - return (V8ValuePromise) v8Native.createV8Value( - handle, V8ValueReferenceType.Promise.getId(), null); + return (V8ValuePromise) v8Native.promiseCreate(handle); } @Override - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue public V8ValueProxy createV8ValueProxy(V8ValueObject v8ValueObject) throws JavetException { - return (V8ValueProxy) v8Native.createV8Value( - handle, V8ValueReferenceType.Proxy.getId(), v8ValueObject); + return (V8ValueProxy) v8Native.proxyCreate(handle, v8ValueObject); } @Override - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue public V8ValueSet createV8ValueSet() throws JavetException { - return (V8ValueSet) v8Native.createV8Value( - handle, V8ValueReferenceType.Set.getId(), null); + return (V8ValueSet) v8Native.setCreate(handle); } @Override @@ -801,15 +845,13 @@ public V8ValueString createV8ValueString(String str) throws JavetException { @Override @CheckReturnValue public V8ValueSymbol createV8ValueSymbol(String description, boolean global) throws JavetException { - Objects.requireNonNull(description); - assert description.length() > 0; + assert description != null && description.length() > 0 : ERROR_SYMBOL_DESCRIPTION_CANNOT_BE_EMPTY; if (global) { try (V8ValueBuiltInSymbol v8ValueBuiltInSymbol = getGlobalObject().getBuiltInSymbol()) { return v8ValueBuiltInSymbol._for(description); } } else { - return (V8ValueSymbol) v8Native.createV8Value( - handle, V8ValueReferenceType.Symbol.getId(), description); + return (V8ValueSymbol) v8Native.symbolCreate(handle, description); } } @@ -840,35 +882,6 @@ public V8ValueZonedDateTime createV8ValueZonedDateTime(ZonedDateTime zonedDateTi return new V8ValueZonedDateTime(this, zonedDateTime); } - /** - * Delete a key from an object. - * - * @param iV8ValueObject the V8 value object - * @param key the key - * @return true : deleted, false : key is not found - * @throws JavetException the javet exception - * @since 0.7.0 - */ - @SuppressWarnings("RedundantThrows") - boolean delete(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { - return v8Native.delete(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); - } - - /** - * Delete a private property from an object. - * - * @param iV8ValueObject the V8 value object - * @param propertyName the property name - * @return true : deleted, false : key is not found - * @throws JavetException the javet exception - * @since 0.9.12 - */ - @SuppressWarnings("RedundantThrows") - boolean deletePrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) throws JavetException { - return v8Native.deletePrivateProperty( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), propertyName); - } - /** * Equals tells whether 2 references are reference equal or not. * @@ -900,10 +913,60 @@ boolean equals(IV8ValueReference iV8ValueReference1, IV8ValueReference iV8ValueR public T execute( String scriptString, byte[] cachedData, V8ScriptOrigin v8ScriptOrigin, boolean resultRequired) throws JavetException { - return (T) v8Native.execute( - handle, scriptString, cachedData, resultRequired, v8ScriptOrigin.getResourceName(), - v8ScriptOrigin.getResourceLineOffset(), v8ScriptOrigin.getResourceColumnOffset(), - v8ScriptOrigin.getScriptId(), v8ScriptOrigin.isWasm(), v8ScriptOrigin.isModule()); + if (v8ScriptOrigin.isModule()) { + return (T) v8Native.moduleExecute( + handle, scriptString, cachedData, resultRequired, v8ScriptOrigin.getResourceName(), + v8ScriptOrigin.getResourceLineOffset(), v8ScriptOrigin.getResourceColumnOffset(), + v8ScriptOrigin.getScriptId(), v8ScriptOrigin.isWasm()); + } else { + return (T) v8Native.scriptExecute( + handle, scriptString, cachedData, resultRequired, v8ScriptOrigin.getResourceName(), + v8ScriptOrigin.getResourceLineOffset(), v8ScriptOrigin.getResourceColumnOffset(), + v8ScriptOrigin.getScriptId(), v8ScriptOrigin.isWasm()); + } + } + + /** + * Call a function. + *

    + * It is similar to JavaScript built-in functions apply() or call(). + * + * @param the type parameter + * @param iV8ValueObject the V8 value object + * @param receiver the receiver + * @param returnResult the return result + * @param v8Values the V8 values + * @return the result + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + T functionCall( + IV8ValueObject iV8ValueObject, IV8ValueObject receiver, boolean returnResult, + V8Value... v8Values) + throws JavetException { + return (T) v8Native.functionCall( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), + receiver, returnResult, v8Values); + } + + /** + * Call a function as a constructor. + * + * @param the type parameter + * @param iV8ValueObject the V8 value object + * @param v8Values the V8 values + * @return the result + * @throws JavetException the javet exception + * @since 0.7.2 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + T functionCallAsConstructor( + IV8ValueObject iV8ValueObject, V8Value... v8Values) throws JavetException { + return (T) v8Native.functionCallAsConstructor( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), v8Values); } /** @@ -962,6 +1025,20 @@ String[] functionGetArguments(IV8ValueFunction iV8ValueFunction) throws JavetExc handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId()); } + /** + * Get cached data from a function. + * + * @param iV8ValueFunction the V8 value function + * @return the cached data + * @throws JavetException the javet exception + * @since 2.0.3 + */ + @SuppressWarnings("RedundantThrows") + byte[] functionGetCachedData(IV8ValueFunction iV8ValueFunction) throws JavetException { + return v8Native.functionGetCachedData( + handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId()); + } + /** * Gets the V8 context. * @@ -977,6 +1054,47 @@ V8Context functionGetContext(IV8ValueFunction iV8ValueFunction) throws JavetExce handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId()); } + /** + * Gets internal properties from a function. + *

    + * This is experimental only. + * + * @param iV8ValueFunction the V8 value function + * @return the internal properties + * @throws JavetException the javet exception + * @since 0.8.8 + */ + @CheckReturnValue + @SuppressWarnings("RedundantThrows") + IV8ValueArray functionGetInternalProperties(IV8ValueFunction iV8ValueFunction) throws JavetException { + return (V8ValueArray) v8Native.functionGetInternalProperties( + handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId()); + } + + /** + * Gets the JS function type from a function. + * + * @param iV8ValueFunction the V8 value function + * @return the JS function type + * @since 0.8.8 + */ + JSFunctionType functionGetJSFunctionType(IV8ValueFunction iV8ValueFunction) { + return JSFunctionType.parse(v8Native.functionGetJSFunctionType( + handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId())); + } + + /** + * Gets js scope type. + * + * @param iV8ValueFunction the V8 value function + * @return the js scope type + * @since 0.8.8 + */ + JSScopeType functionGetJSScopeType(IV8ValueFunction iV8ValueFunction) { + return JSScopeType.parse(v8Native.functionGetJSScopeType( + handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId())); + } + /** * Gets scope infos from a V8 value function. * @@ -985,6 +1103,7 @@ V8Context functionGetContext(IV8ValueFunction iV8ValueFunction) throws JavetExce * @return the V8 value array * @throws JavetException the javet exception */ + @SuppressWarnings("RedundantThrows") IV8ValueArray functionGetScopeInfos( IV8ValueFunction iV8ValueFunction, IV8ValueFunction.GetScopeInfosOptions options) @@ -1099,64 +1218,6 @@ boolean functionSetSourceCode( handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId(), sourceCode, cloneScript); } - /** - * Get a property from an object by a property key. - * - * @param the type parameter - * @param iV8ValueObject the V8 value object - * @param key the property key - * @return the property value - * @throws JavetException the javet exception - * @since 0.7.0 - */ - @CheckReturnValue - T get(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { - return (T) v8Native.get( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); - } - - /** - * Get cached data from a function. - * - * @param iV8ValueFunction the V8 value function - * @return the cached data - * @throws JavetException the javet exception - * @since 2.0.3 - */ - @SuppressWarnings("RedundantThrows") - byte[] getCachedData(IV8ValueFunction iV8ValueFunction) throws JavetException { - return v8Native.getCachedData( - handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId()); - } - - /** - * Get cached data from a module. - * - * @param iV8Module the V8 module - * @return the cached data - * @throws JavetException the javet exception - * @since 2.0.3 - */ - @SuppressWarnings("RedundantThrows") - byte[] getCachedData(IV8Module iV8Module) throws JavetException { - return v8Native.getCachedData( - handle, iV8Module.getHandle(), iV8Module.getType().getId()); - } - - /** - * Get cached data from a script. - * - * @param iV8Script the V8 script - * @return the cached data - * @throws JavetException the javet exception - * @since 2.0.3 - */ - @SuppressWarnings("RedundantThrows") - byte[] getCachedData(IV8Script iV8Script) throws JavetException { - return v8Native.getCachedData( - handle, iV8Script.getHandle(), iV8Script.getType().getId()); - } - /** * Gets a callback context by a handle. * @@ -1258,48 +1319,6 @@ public long getHandle() { return handle; } - /** - * Gets the internal identity hash by a reference object. - * - * @param iV8ValueReference the V8 value reference - * @return the identity hash - * @throws JavetException the javet exception - * @since 0.9.1 - */ - @SuppressWarnings("RedundantThrows") - int getIdentityHash(IV8ValueReference iV8ValueReference) throws JavetException { - return v8Native.getIdentityHash(handle, iV8ValueReference.getHandle(), iV8ValueReference.getType().getId()); - } - - /** - * Gets internal properties from a function. - *

    - * This is experimental only. - * - * @param iV8ValueFunction the V8 value function - * @return the internal properties - * @throws JavetException the javet exception - * @since 0.8.8 - */ - @CheckReturnValue - @SuppressWarnings("RedundantThrows") - IV8ValueArray getInternalProperties(IV8ValueFunction iV8ValueFunction) throws JavetException { - return (V8ValueArray) v8Native.getInternalProperties( - handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId()); - } - - /** - * Gets the JS function type from a function. - * - * @param iV8ValueFunction the V8 value function - * @return the JS function type - * @since 0.8.8 - */ - JSFunctionType getJSFunctionType(IV8ValueFunction iV8ValueFunction) { - return JSFunctionType.parse(v8Native.getJSFunctionType( - handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId())); - } - /** * Gets the JS runtime type. * @@ -1310,44 +1329,6 @@ public JSRuntimeType getJSRuntimeType() { return JSRuntimeType.V8; } - /** - * Gets js scope type. - * - * @param iV8ValueFunction the V8 value function - * @return the js scope type - * @since 0.8.8 - */ - JSScopeType getJSScopeType(IV8ValueFunction iV8ValueFunction) { - return JSScopeType.parse(v8Native.getJSScopeType( - handle, iV8ValueFunction.getHandle(), iV8ValueFunction.getType().getId())); - } - - /** - * Gets length from an array. - * - * @param iV8ValueArray the V8 value array - * @return the length - * @throws JavetException the javet exception - * @since 0.7.0 - */ - @SuppressWarnings("RedundantThrows") - int getLength(IV8ValueArray iV8ValueArray) throws JavetException { - return v8Native.getLength(handle, iV8ValueArray.getHandle(), iV8ValueArray.getType().getId()); - } - - /** - * Gets length from a typed array. - * - * @param iV8ValueTypedArray the V8 value typed array - * @return the length - * @throws JavetException the javet exception - * @since 0.8.4 - */ - @SuppressWarnings("RedundantThrows") - int getLength(IV8ValueTypedArray iV8ValueTypedArray) throws JavetException { - return v8Native.getLength(handle, iV8ValueTypedArray.getHandle(), iV8ValueTypedArray.getType().getId()); - } - /** * Gets the internal logger. * @@ -1358,40 +1339,6 @@ public IJavetLogger getLogger() { return logger; } - /** - * Gets own property names from an object. - * - * @param iV8ValueObject the V8 value object - * @return the own property names - * @throws JavetException the javet exception - * @since 0.7.0 - */ - @CheckReturnValue - @SuppressWarnings("RedundantThrows") - IV8ValueArray getOwnPropertyNames( - IV8ValueObject iV8ValueObject) throws JavetException { - return (V8ValueArray) v8Native.getOwnPropertyNames( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId()); - } - - /** - * Gets a private property from an object by a property name. - * - * @param the type parameter - * @param iV8ValueObject the V8 value object - * @param propertyName the property name - * @return the private property - * @throws JavetException the javet exception - * @since 0.9.12 - */ - @CheckReturnValue - @SuppressWarnings("RedundantThrows") - T getPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) - throws JavetException { - return (T) v8Native.getPrivateProperty( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), propertyName); - } - /** * Gets promise reject callback. * @@ -1402,54 +1349,6 @@ public IJavetPromiseRejectCallback getPromiseRejectCallback() { return promiseRejectCallback; } - /** - * Gets a property from an object by a property key. - * - * @param the type parameter - * @param iV8ValueObject the V8 value object - * @param key the property key - * @return the property - * @throws JavetException the javet exception - * @since 0.7.0 - */ - @CheckReturnValue - @SuppressWarnings("RedundantThrows") - T getProperty(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { - return (T) v8Native.getProperty( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); - } - - /** - * Gets property names from an object. - * - * @param iV8ValueObject the V8 value object - * @return the property names - * @throws JavetException the javet exception - * @since 0.7.0 - */ - @CheckReturnValue - @SuppressWarnings("RedundantThrows") - IV8ValueArray getPropertyNames(IV8ValueObject iV8ValueObject) throws JavetException { - return (V8ValueArray) v8Native.getPropertyNames( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId()); - } - - /** - * Gets prototype from an object. - * - * @param the type parameter - * @param iV8ValueObject the V8 value object - * @return the prototype - * @throws JavetException the javet exception - * @since 0.9.4 - */ - @CheckReturnValue - @SuppressWarnings("RedundantThrows") - T getPrototype(IV8ValueObject iV8ValueObject) throws JavetException { - return (T) v8Native.getPrototype( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId()); - } - /** * Gets the internal reference count. * @@ -1470,19 +1369,6 @@ public RuntimeOptions getRuntimeOptions() { return runtimeOptions; } - /** - * Gets size from a key container. - * - * @param iV8ValueKeyContainer the V8 value key container - * @return the size - * @throws JavetException the javet exception - * @since 0.7.0 - */ - @SuppressWarnings("RedundantThrows") - int getSize(IV8ValueKeyContainer iV8ValueKeyContainer) throws JavetException { - return v8Native.getSize(handle, iV8ValueKeyContainer.getHandle(), iV8ValueKeyContainer.getType().getId()); - } - /** * Gets V8 heap space statistics by an allocation space. * @@ -1632,20 +1518,6 @@ public String getVersion() { return v8Native.getVersion(); } - /** - * Has a property in an object. - * - * @param iV8ValueObject the V8 value object - * @param value the value - * @return true : yes, false : no - * @throws JavetException the javet exception - * @since 0.7.2 - */ - @SuppressWarnings("RedundantThrows") - boolean has(IV8ValueObject iV8ValueObject, V8Value value) throws JavetException { - return v8Native.has(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), value); - } - /** * Has internal type. * @@ -1659,20 +1531,6 @@ boolean hasInternalType(IV8ValueObject iV8ValueObject, V8ValueInternalType inter handle, iV8ValueObject.getHandle(), Objects.requireNonNull(internalType).getId()); } - /** - * Has own property in an object by a property key. - * - * @param iV8ValueObject the V8 value object - * @param key the property key - * @return true : yes, false : no - * @throws JavetException the javet exception - * @since 0.7.2 - */ - @SuppressWarnings("RedundantThrows") - boolean hasOwnProperty(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { - return v8Native.hasOwnProperty(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); - } - /** * Has pending exception. * @@ -1697,21 +1555,6 @@ public boolean hasPendingMessage() throws JavetException { return v8Native.hasPendingMessage(handle); } - /** - * Has private property in an object by a property name. - * - * @param iV8ValueObject the V8 value object - * @param propertyName the property name - * @return true : yes, false : no - * @throws JavetException the javet exception - * @since 0.9.12 - */ - @SuppressWarnings("RedundantThrows") - boolean hasPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) throws JavetException { - return v8Native.hasPrivateProperty( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), propertyName); - } - /** * Has scheduled exception. * @@ -1763,27 +1606,6 @@ void initializeV8ValueCache() { } } - /** - * Invoke a function by a function name. - * - * @param the type parameter - * @param iV8ValueObject the V8 value object - * @param functionName the function name - * @param returnResult the return result - * @param v8Values the V8 values - * @return the result - * @throws JavetException the javet exception - * @since 0.7.0 - */ - @CheckReturnValue - @SuppressWarnings("RedundantThrows") - T invoke( - IV8ValueObject iV8ValueObject, String functionName, boolean returnResult, V8Value... v8Values) - throws JavetException { - return (T) v8Native.invoke( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), functionName, returnResult, v8Values); - } - @Override public boolean isClosed() { return handle == INVALID_HANDLE; @@ -1820,124 +1642,951 @@ public boolean isInUse() { } /** - * Returns whether the V8 runtime is managed by a pool or not. + * Returns whether the V8 runtime is managed by a pool or not. + * + * @return true : yes, false : no + * @since 0.7.0 + */ + public boolean isPooled() { + return pooled; + } + + /** + * Returns whether the reference is weak or not. + * + * @param iV8ValueReference the V8 value reference + * @return true : weak, false : strong + * @since 0.7.0 + */ + boolean isWeak(IV8ValueReference iV8ValueReference) { + return v8Native.isWeak(handle, iV8ValueReference.getHandle(), iV8ValueReference.getType().getId()); + } + + /** + * Send low memory notification to current V8 isolate. + * + * @since 0.8.3 + */ + public void lowMemoryNotification() { + if (!isClosed()) { + v8Native.lowMemoryNotification(handle); + } + } + + /** + * Delete a key from a map. + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @return true : deleted, false : key is not found + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapDelete(IV8ValueMap iV8ValueMap, V8Value key) throws JavetException { + return v8Native.mapDelete(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key); + } + + /** + * Get a property from a map by a key. + * + * @param the type parameter + * @param iV8ValueMap the v 8 value map + * @param key the property key + * @return the property value + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + T mapGet(IV8ValueMap iV8ValueMap, V8Value key) throws JavetException { + return (T) v8Native.mapGet( + handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key); + } + + /** + * Get Boolean from a map by key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @return the boolean + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + Boolean mapGetBoolean( + IV8ValueMap iV8ValueMap, V8Value key) + throws JavetException { + primitiveFlags[0] = true; + boolean value = v8Native.mapGetBoolean( + handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key, primitiveFlags); + return primitiveFlags[0] ? value : null; + } + + /** + * Get Double from a map by key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @return the double + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + Double mapGetDouble( + IV8ValueMap iV8ValueMap, V8Value key) + throws JavetException { + primitiveFlags[0] = true; + double value = v8Native.mapGetDouble( + handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key, primitiveFlags); + return primitiveFlags[0] ? value : null; + } + + /** + * Get Integer from a map by key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @return the int + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + Integer mapGetInteger( + IV8ValueMap iV8ValueMap, V8Value key) + throws JavetException { + primitiveFlags[0] = true; + int value = v8Native.mapGetInteger( + handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key, primitiveFlags); + return primitiveFlags[0] ? value : null; + } + + /** + * Get Long from a map by key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @return the long + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + Long mapGetLong( + IV8ValueMap iV8ValueMap, V8Value key) + throws JavetException { + primitiveFlags[0] = true; + long value = v8Native.mapGetLong( + handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key, primitiveFlags); + return primitiveFlags[0] ? value : null; + } + + /** + * Gets size from a map. + * + * @param iV8ValueMap the V8 value map + * @return the size + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + int mapGetSize(IV8ValueMap iV8ValueMap) throws JavetException { + return v8Native.mapGetSize(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId()); + } + + /** + * Get String from a map by key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @return the String + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + String mapGetString( + IV8ValueMap iV8ValueMap, V8Value key) + throws JavetException { + return v8Native.mapGetString( + handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key); + } + + /** + * Has a property in a map. + * + * @param iV8ValueMap the V8 value map + * @param value the value + * @return true : yes, false : no + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapHas(IV8ValueMap iV8ValueMap, V8Value value) throws JavetException { + return v8Native.mapHas(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), value); + } + + /** + * Sets a property of a map by a key + * + * @param iV8ValueMap the V8 value map + * @param v8Values the V8 values + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapSet(IV8ValueMap iV8ValueMap, V8Value... v8Values) throws JavetException { + assert v8Values.length > 0 && v8Values.length % 2 == 0 : ERROR_THE_KEY_VALUE_PAIR_MUST_MATCH; + return v8Native.mapSet(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), v8Values); + } + + /** + * Sets a property of a map to a boolean value by a key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @param value the value + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapSetBoolean( + IV8ValueMap iV8ValueMap, V8Value key, boolean value) + throws JavetException { + return v8Native.mapSetBoolean(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key, value); + } + + /** + * Sets a property of a map to a double value by a key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @param value the value + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapSetDouble( + IV8ValueMap iV8ValueMap, V8Value key, double value) + throws JavetException { + return v8Native.mapSetDouble(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key, value); + } + + /** + * Sets a property of a map to an int value by a key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @param value the value + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapSetInteger( + IV8ValueMap iV8ValueMap, V8Value key, int value) + throws JavetException { + return v8Native.mapSetInteger(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key, value); + } + + /** + * Sets a property of a map to a long value by a key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @param value the value + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapSetLong( + IV8ValueMap iV8ValueMap, V8Value key, long value) + throws JavetException { + return v8Native.mapSetLong(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key, value); + } + + /** + * Sets a property of a map to null by a key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapSetNull(IV8ValueMap iV8ValueMap, V8Value key) throws JavetException { + return v8Native.mapSetNull(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key); + } + + /** + * Sets a property of a map to a string value by a key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @param value the value + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapSetString( + IV8ValueMap iV8ValueMap, V8Value key, String value) + throws JavetException { + return v8Native.mapSetString(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key, value); + } + + /** + * Sets a property of a map to undefined by a key + * + * @param iV8ValueMap the V8 value map + * @param key the key + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean mapSetUndefined(IV8ValueMap iV8ValueMap, V8Value key) throws JavetException { + return v8Native.mapSetUndefined(handle, iV8ValueMap.getHandle(), iV8ValueMap.getType().getId(), key); + } + + /** + * Evaluate a module. + * + * @param the type parameter + * @param iV8Module the V8 module + * @param resultRequired the result required + * @return the result + * @throws JavetException the javet exception + * @since 0.8.0 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + T moduleEvaluate( + IV8Module iV8Module, boolean resultRequired) throws JavetException { + return (T) v8Native.moduleEvaluate( + handle, iV8Module.getHandle(), iV8Module.getType().getId(), resultRequired); + } + + /** + * Get cached data from a module. + * + * @param iV8Module the V8 module + * @return the cached data + * @throws JavetException the javet exception + * @since 2.0.3 + */ + @SuppressWarnings("RedundantThrows") + byte[] moduleGetCachedData(IV8Module iV8Module) throws JavetException { + return v8Native.moduleGetCachedData( + handle, iV8Module.getHandle(), iV8Module.getType().getId()); + } + + /** + * Gets an error from a module. + * + * @param iV8Module the V8 module + * @return the V8 value error + * @throws JavetException the javet exception + * @since 0.9.12 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + V8ValueError moduleGetException(IV8Module iV8Module) throws JavetException { + return (V8ValueError) v8Native.moduleGetException( + handle, iV8Module.getHandle(), iV8Module.getType().getId()); + } + + /** + * Gets the namespace from a module. + * + * @param iV8Module the V8 module + * @return the namespace + * @throws JavetException the javet exception + * @since 0.8.0 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + V8ValueObject moduleGetNamespace(IV8Module iV8Module) throws JavetException { + return (V8ValueObject) v8Native.moduleGetNamespace( + handle, iV8Module.getHandle(), iV8Module.getType().getId()); + } + + /** + * Gets the script ID from a module. + * + * @param iV8Module the V8 module + * @return the script ID + * @throws JavetException the javet exception + * @since 0.8.4 + */ + @SuppressWarnings("RedundantThrows") + int moduleGetScriptId(IV8Module iV8Module) throws JavetException { + return v8Native.moduleGetScriptId(handle, iV8Module.getHandle(), iV8Module.getType().getId()); + } + + /** + * Gets the status from a module. + * + * @param iV8Module the V8 module + * @return the status + * @throws JavetException the javet exception + * @since 0.8.4 + */ + @SuppressWarnings("RedundantThrows") + int moduleGetStatus(IV8Module iV8Module) throws JavetException { + return v8Native.moduleGetStatus(handle, iV8Module.getHandle(), iV8Module.getType().getId()); + } + + /** + * Instantiate a module. + *

    + * It may return an exception or false if the module state is invalid. + * + * @param iV8Module the V8 module + * @return true : success, false : false + * @throws JavetException the javet exception + * @since 0.8.4 + */ + @SuppressWarnings("RedundantThrows") + boolean moduleInstantiate(IV8Module iV8Module) throws JavetException { + return v8Native.moduleInstantiate(handle, iV8Module.getHandle(), iV8Module.getType().getId()); + } + + /** + * Delete a key from an object. + * + * @param iV8ValueObject the V8 value object + * @param key the key + * @return true : deleted, false : key is not found + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + boolean objectDelete(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Native.objectDelete(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); + } + + /** + * Delete a private property from an object. + * + * @param iV8ValueObject the V8 value object + * @param propertyName the property name + * @return true : deleted, false : key is not found + * @throws JavetException the javet exception + * @since 0.9.12 + */ + @SuppressWarnings("RedundantThrows") + boolean objectDeletePrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) throws JavetException { + return v8Native.objectDeletePrivateProperty( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), propertyName); + } + + /** + * Get a property from an object by a property key. + * + * @param the type parameter + * @param iV8ValueObject the V8 value object + * @param key the property key + * @return the property value + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + T objectGet(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return (T) v8Native.objectGet( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); + } + + /** + * Get Boolean from an object by key + * + * @param iV8ValueObject the V8 value object + * @param key the key + * @return the boolean + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + Boolean objectGetBoolean( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + primitiveFlags[0] = true; + boolean value = v8Native.objectGetBoolean( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, primitiveFlags); + return primitiveFlags[0] ? value : null; + } + + /** + * Get Double from an object by key + * + * @param iV8ValueObject the V8 value object + * @param key the key + * @return the double + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + Double objectGetDouble( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + primitiveFlags[0] = true; + double value = v8Native.objectGetDouble( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, primitiveFlags); + return primitiveFlags[0] ? value : null; + } + + /** + * Gets the internal identity hash by a reference object. + * + * @param iV8ValueReference the V8 value reference + * @return the identity hash + * @throws JavetException the javet exception + * @since 0.9.1 + */ + @SuppressWarnings("RedundantThrows") + int objectGetIdentityHash(IV8ValueReference iV8ValueReference) throws JavetException { + return v8Native.objectGetIdentityHash( + handle, iV8ValueReference.getHandle(), iV8ValueReference.getType().getId()); + } + + /** + * Get Integer from an object by key + * + * @param iV8ValueObject the V8 value object + * @param key the key + * @return the int + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + Integer objectGetInteger( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + primitiveFlags[0] = true; + int value = v8Native.objectGetInteger( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, primitiveFlags); + return primitiveFlags[0] ? value : null; + } + + /** + * Get Long from an object by key + * + * @param iV8ValueObject the V8 value object + * @param key the key + * @return the long + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + Long objectGetLong( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + primitiveFlags[0] = true; + long value = v8Native.objectGetLong( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, primitiveFlags); + return primitiveFlags[0] ? value : null; + } + + /** + * Gets own property names from an object. + * + * @param iV8ValueObject the V8 value object + * @return the own property names + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + IV8ValueArray objectGetOwnPropertyNames( + IV8ValueObject iV8ValueObject) throws JavetException { + return (V8ValueArray) v8Native.objectGetOwnPropertyNames( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId()); + } + + /** + * Gets a private property from an object by a property name. + * + * @param the type parameter + * @param iV8ValueObject the V8 value object + * @param propertyName the property name + * @return the private property + * @throws JavetException the javet exception + * @since 0.9.12 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + T objectGetPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) + throws JavetException { + return (T) v8Native.objectGetPrivateProperty( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), propertyName); + } + + /** + * Gets a property from an object by a property key. + * + * @param the type parameter + * @param iV8ValueObject the V8 value object + * @param key the property key + * @return the property + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + T objectGetProperty(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return (T) v8Native.objectGetProperty( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); + } + + /** + * Gets property names from an object. + * + * @param iV8ValueObject the V8 value object + * @return the property names + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + IV8ValueArray objectGetPropertyNames(IV8ValueObject iV8ValueObject) throws JavetException { + return (V8ValueArray) v8Native.objectGetPropertyNames( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId()); + } + + /** + * Gets prototype from an object. + * + * @param the type parameter + * @param iV8ValueObject the V8 value object + * @return the prototype + * @throws JavetException the javet exception + * @since 0.9.4 + */ + @CheckReturnValue + @SuppressWarnings("RedundantThrows") + T objectGetPrototype(IV8ValueObject iV8ValueObject) throws JavetException { + return (T) v8Native.objectGetPrototype( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId()); + } + + /** + * Get String from an object by key + * + * @param iV8ValueObject the V8 value object + * @param key the key + * @return the String + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + String objectGetString( + IV8ValueObject iV8ValueObject, V8Value key) + throws JavetException { + return v8Native.objectGetString( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); + } + + /** + * Has a property in an object. + * + * @param iV8ValueObject the V8 value object + * @param propertyKey the property key + * @return true : yes, false : no + * @throws JavetException the javet exception + * @since 0.7.2 + */ + @SuppressWarnings("RedundantThrows") + boolean objectHas(IV8ValueObject iV8ValueObject, V8Value propertyKey) throws JavetException { + return v8Native.objectHas(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), propertyKey); + } + + /** + * Has own property in an object by a property key. + * + * @param iV8ValueObject the V8 value object + * @param key the property key + * @return true : yes, false : no + * @throws JavetException the javet exception + * @since 0.7.2 + */ + @SuppressWarnings("RedundantThrows") + boolean objectHasOwnProperty(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Native.objectHasOwnProperty(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); + } + + /** + * Has private property in an object by a property name. + * + * @param iV8ValueObject the V8 value object + * @param propertyName the property name + * @return true : yes, false : no + * @throws JavetException the javet exception + * @since 0.9.12 + */ + @SuppressWarnings("RedundantThrows") + boolean objectHasPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName) throws JavetException { + return v8Native.objectHasPrivateProperty( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), propertyName); + } + + /** + * Invoke a function by a function name. + * + * @param the type parameter + * @param iV8ValueObject the V8 value object + * @param functionName the function name + * @param returnResult the return result + * @param v8Values the V8 values + * @return the result + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + @CheckReturnValue + T objectInvoke( + IV8ValueObject iV8ValueObject, String functionName, boolean returnResult, V8Value... v8Values) + throws JavetException { + return (T) v8Native.objectInvoke( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), functionName, returnResult, v8Values); + } + + /** + * Sets a property of an object by a key + * + * @param iV8ValueObject the V8 value object + * @param v8Values the V8 values + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 0.7.0 + */ + @SuppressWarnings("RedundantThrows") + boolean objectSet(IV8ValueObject iV8ValueObject, V8Value... v8Values) throws JavetException { + assert v8Values.length > 0 && v8Values.length % 2 == 0 : ERROR_THE_KEY_VALUE_PAIR_MUST_MATCH; + return v8Native.objectSet(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), v8Values); + } + + /** + * Sets accessor (getter / setter) by a property name. + * + * @param iV8ValueObject the V8 value object + * @param propertyName the property name + * @param javetCallbackContextGetter the javet callback context getter + * @param javetCallbackContextSetter the javet callback context setter + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 0.8.9 + */ + @SuppressWarnings("RedundantThrows") + boolean objectSetAccessor( + IV8ValueObject iV8ValueObject, + V8Value propertyName, + JavetCallbackContext javetCallbackContextGetter, + JavetCallbackContext javetCallbackContextSetter) throws JavetException { + assert (propertyName instanceof V8ValueString || propertyName instanceof V8ValueSymbol) + : ERROR_THE_PROPERTY_NAME_MUST_BE_EITHER_STRING_OR_SYMBOL; + boolean isAccessorSet = v8Native.objectSetAccessor( + handle, + iV8ValueObject.getHandle(), + iV8ValueObject.getType().getId(), + propertyName, + javetCallbackContextGetter, + javetCallbackContextSetter); + synchronized (callbackContextLock) { + if (javetCallbackContextGetter != null && javetCallbackContextGetter.isValid()) { + callbackContextMap.put(javetCallbackContextGetter.getHandle(), javetCallbackContextGetter); + } + if (javetCallbackContextSetter != null && javetCallbackContextSetter.isValid()) { + callbackContextMap.put(javetCallbackContextSetter.getHandle(), javetCallbackContextSetter); + } + } + return isAccessorSet; + } + + /** + * Sets a property of an object to a boolean value by a key + * + * @param iV8ValueObject the V8 value object + * @param key the key + * @param value the value + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean objectSetBoolean( + IV8ValueObject iV8ValueObject, V8Value key, boolean value) + throws JavetException { + return v8Native.objectSetBoolean( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, value); + } + + /** + * Sets a property of an object to a double value by a key + * + * @param iV8ValueObject the V8 value object + * @param key the key + * @param value the value + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("RedundantThrows") + boolean objectSetDouble( + IV8ValueObject iV8ValueObject, V8Value key, double value) + throws JavetException { + return v8Native.objectSetDouble( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, value); + } + + /** + * Sets a property of an object to an int value by a key * - * @return true : yes, false : no - * @since 0.7.0 + * @param iV8ValueObject the V8 value object + * @param key the key + * @param value the value + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 */ - public boolean isPooled() { - return pooled; + @SuppressWarnings("RedundantThrows") + boolean objectSetInteger( + IV8ValueObject iV8ValueObject, V8Value key, int value) + throws JavetException { + return v8Native.objectSetInteger( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, value); } /** - * Returns whether the reference is weak or not. + * Sets a property of an object to a long value by a key * - * @param iV8ValueReference the V8 value reference - * @return true : weak, false : strong - * @since 0.7.0 + * @param iV8ValueObject the V8 value object + * @param key the key + * @param value the value + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 */ - boolean isWeak(IV8ValueReference iV8ValueReference) { - return v8Native.isWeak(handle, iV8ValueReference.getHandle(), iV8ValueReference.getType().getId()); + @SuppressWarnings("RedundantThrows") + boolean objectSetLong( + IV8ValueObject iV8ValueObject, V8Value key, long value) + throws JavetException { + return v8Native.objectSetLong( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, value); } /** - * Send low memory notification to current V8 isolate. + * Sets a property of an object to null by a key * - * @since 0.8.3 + * @param iV8ValueObject the V8 value object + * @param key the key + * @return true : success, false : failure + * @throws JavetException the javet exception + * @since 2.2.0 */ - public void lowMemoryNotification() { - if (!isClosed()) { - v8Native.lowMemoryNotification(handle); - } + @SuppressWarnings("RedundantThrows") + boolean objectSetNull(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Native.objectSetNull(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); } /** - * Evaluate a module. + * Sets a private property. * - * @param the type parameter - * @param iV8Module the V8 module - * @param resultRequired the result required - * @return the result + * @param iV8ValueObject the V8 value object + * @param propertyName the property name + * @param propertyValue the property value + * @return true : success, false : failure * @throws JavetException the javet exception - * @since 0.8.0 + * @since 0.9.12 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") - T moduleEvaluate( - IV8Module iV8Module, boolean resultRequired) throws JavetException { - return (T) v8Native.moduleEvaluate( - handle, iV8Module.getHandle(), iV8Module.getType().getId(), resultRequired); + boolean objectSetPrivateProperty( + IV8ValueObject iV8ValueObject, String propertyName, V8Value propertyValue) + throws JavetException { + return v8Native.objectSetPrivateProperty( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), propertyName, propertyValue); } /** - * Gets an error from a module. + * Sets property. * - * @param iV8Module the V8 module - * @return the V8 value error + * @param iV8ValueObject the V8 value object + * @param key the key + * @param value the value + * @return true : success, false : failure * @throws JavetException the javet exception - * @since 0.9.12 + * @since 0.7.0 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") - V8ValueError moduleGetException(IV8Module iV8Module) throws JavetException { - return (V8ValueError) v8Native.moduleGetException( - handle, iV8Module.getHandle(), iV8Module.getType().getId()); + boolean objectSetProperty(IV8ValueObject iV8ValueObject, V8Value key, V8Value value) throws JavetException { + return v8Native.objectSetProperty( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, value); } /** - * Gets the namespace from a module. + * Sets prototype. * - * @param iV8Module the V8 module - * @return the namespace + * @param iV8ValueObject the V8 value object + * @param iV8ValueObjectPrototype the V8 value object prototype + * @return true : success, false : failure * @throws JavetException the javet exception - * @since 0.8.0 + * @since 0.9.4 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") - V8ValueObject moduleGetNamespace(IV8Module iV8Module) throws JavetException { - return (V8ValueObject) v8Native.moduleGetNamespace( - handle, iV8Module.getHandle(), iV8Module.getType().getId()); + boolean objectSetPrototype( + IV8ValueObject iV8ValueObject, IV8ValueObject iV8ValueObjectPrototype) + throws JavetException { + return v8Native.objectSetPrototype( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), + iV8ValueObjectPrototype.getHandle()); } /** - * Gets the script ID from a module. + * Sets a property of an object to a string value by a key * - * @param iV8Module the V8 module - * @return the script ID + * @param iV8ValueObject the V8 value object + * @param key the key + * @param value the value + * @return true : success, false : failure * @throws JavetException the javet exception - * @since 0.8.4 + * @since 2.2.0 */ @SuppressWarnings("RedundantThrows") - int moduleGetScriptId(IV8Module iV8Module) throws JavetException { - return v8Native.moduleGetScriptId(handle, iV8Module.getHandle(), iV8Module.getType().getId()); + boolean objectSetString( + IV8ValueObject iV8ValueObject, V8Value key, String value) + throws JavetException { + return v8Native.objectSetString( + handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, value); } /** - * Gets the status from a module. + * Sets a property of an object to undefined by a key * - * @param iV8Module the V8 module - * @return the status + * @param iV8ValueObject the V8 value object + * @param key the key + * @return true : success, false : failure * @throws JavetException the javet exception - * @since 0.8.4 + * @since 2.2.0 */ @SuppressWarnings("RedundantThrows") - int moduleGetStatus(IV8Module iV8Module) throws JavetException { - return v8Native.moduleGetStatus(handle, iV8Module.getHandle(), iV8Module.getType().getId()); + boolean objectSetUndefined(IV8ValueObject iV8ValueObject, V8Value key) throws JavetException { + return v8Native.objectSetUndefined(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key); } /** - * Instantiate a module. - *

    - * It may return an exception or false if the module state is invalid. + * Gets a proto string from a reference. * - * @param iV8Module the V8 module - * @return true : success, false : false + * @param iV8ValueReference the V8 value reference + * @return the proto string * @throws JavetException the javet exception * @since 0.8.4 */ @SuppressWarnings("RedundantThrows") - boolean moduleInstantiate(IV8Module iV8Module) throws JavetException { - return v8Native.moduleInstantiate(handle, iV8Module.getHandle(), iV8Module.getType().getId()); + String objectToProtoString(IV8ValueReference iV8ValueReference) throws JavetException { + return v8Native.objectToProtoString(handle, iV8ValueReference.getHandle(), iV8ValueReference.getType().getId()); } /** @@ -1950,8 +2599,8 @@ boolean moduleInstantiate(IV8Module iV8Module) throws JavetException { * @throws JavetException the javet exception * @since 0.8.0 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue T promiseCatch( IV8ValuePromise iV8ValuePromise, IV8ValueFunction functionHandle) throws JavetException { return (T) v8Native.promiseCatch( @@ -1966,8 +2615,8 @@ T promiseCatch( * @throws JavetException the javet exception * @since 0.9.8 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue V8ValuePromise promiseGetPromise(IV8ValuePromise iV8ValuePromise) throws JavetException { return (V8ValuePromise) v8Native.promiseGetPromise( handle, iV8ValuePromise.getHandle(), iV8ValuePromise.getType().getId()); @@ -1982,8 +2631,8 @@ V8ValuePromise promiseGetPromise(IV8ValuePromise iV8ValuePromise) throws JavetEx * @throws JavetException the javet exception * @since 0.8.0 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue T promiseGetResult(IV8ValuePromise iV8ValuePromise) throws JavetException { return (T) v8Native.promiseGetResult( handle, iV8ValuePromise.getHandle(), iV8ValuePromise.getType().getId()); @@ -2058,8 +2707,8 @@ boolean promiseResolve(V8ValuePromise v8ValuePromise, V8Value v8Value) { * @throws JavetException the javet exception * @since 0.8.0 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue T promiseThen( IV8ValuePromise iV8ValuePromise, IV8ValueFunction functionFulfilledHandle, IV8ValueFunction functionRejectedHandle) throws JavetException { @@ -2089,8 +2738,8 @@ public boolean promoteScheduledException() throws JavetException { * @throws JavetException the javet exception * @since 0.9.6 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue V8ValueObject proxyGetHandler(IV8ValueProxy iV8ValueProxy) throws JavetException { return (V8ValueObject) v8Native.proxyGetHandler( handle, iV8ValueProxy.getHandle(), iV8ValueProxy.getType().getId()); @@ -2104,8 +2753,8 @@ V8ValueObject proxyGetHandler(IV8ValueProxy iV8ValueProxy) throws JavetException * @throws JavetException the javet exception * @since 0.9.6 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue V8ValueObject proxyGetTarget(IV8ValueProxy iV8ValueProxy) throws JavetException { return (V8ValueObject) v8Native.proxyGetTarget( handle, iV8ValueProxy.getHandle(), iV8ValueProxy.getType().getId()); @@ -2477,6 +3126,19 @@ boolean sameValue(IV8ValueObject iV8ValueObject1, IV8ValueObject iV8ValueObject2 return v8Native.sameValue(handle, iV8ValueObject1.getHandle(), iV8ValueObject2.getHandle()); } + /** + * Get cached data from a script. + * + * @param iV8Script the V8 script + * @return the cached data + * @throws JavetException the javet exception + * @since 2.0.3 + */ + @SuppressWarnings("RedundantThrows") + byte[] scriptGetCachedData(IV8Script iV8Script) throws JavetException { + return v8Native.scriptGetCachedData(handle, iV8Script.getHandle(), iV8Script.getType().getId()); + } + /** * Run a script. * @@ -2487,8 +3149,8 @@ boolean sameValue(IV8ValueObject iV8ValueObject1, IV8ValueObject iV8ValueObject2 * @throws JavetException the javet exception * @since 0.8.0 */ - @CheckReturnValue @SuppressWarnings("RedundantThrows") + @CheckReturnValue T scriptRun( IV8Script iV8Script, boolean resultRequired) throws JavetException { return (T) v8Native.scriptRun( @@ -2496,49 +3158,16 @@ T scriptRun( } /** - * Sets a property by a key + * Add a value to a set. * - * @param iV8ValueObject the V8 value object - * @param key the key - * @param value the value - * @return true : success, false : failure + * @param iV8ValueSet the V8 value set + * @param value the value * @throws JavetException the javet exception * @since 0.7.0 */ @SuppressWarnings("RedundantThrows") - boolean set(IV8ValueObject iV8ValueObject, V8Value key, V8Value value) throws JavetException { - return v8Native.set(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, value); - } - - /** - * Sets accessor (getter / setter) by a property name. - * - * @param iV8ValueObject the V8 value object - * @param propertyName the property name - * @param javetCallbackContextGetter the javet callback context getter - * @param javetCallbackContextSetter the javet callback context setter - * @return true : success, false : failure - * @throws JavetException the javet exception - * @since 0.8.9 - */ - @SuppressWarnings("RedundantThrows") - boolean setAccessor( - IV8ValueObject iV8ValueObject, - V8Value propertyName, - JavetCallbackContext javetCallbackContextGetter, - JavetCallbackContext javetCallbackContextSetter) throws JavetException { - assert (propertyName instanceof V8ValueString || propertyName instanceof V8ValueSymbol); - boolean isAccessorSet = v8Native.setAccessor(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), - propertyName, javetCallbackContextGetter, javetCallbackContextSetter); - synchronized (callbackContextLock) { - if (javetCallbackContextGetter != null && javetCallbackContextGetter.isValid()) { - callbackContextMap.put(javetCallbackContextGetter.getHandle(), javetCallbackContextGetter); - } - if (javetCallbackContextSetter != null && javetCallbackContextSetter.isValid()) { - callbackContextMap.put(javetCallbackContextSetter.getHandle(), javetCallbackContextSetter); - } - } - return isAccessorSet; + void setAdd(IV8ValueSet iV8ValueSet, V8Value value) throws JavetException { + v8Native.setAdd(handle, iV8ValueSet.getHandle(), iV8ValueSet.getType().getId(), value); } /** @@ -2553,84 +3182,75 @@ public void setConverter(IJavetConverter converter) { } /** - * Sets GC scheduled. + * Delete a key from a set. * - * @param gcScheduled the GC scheduled - * @since 0.9.1 + * @param iV8ValueSet the v 8 value set + * @param key the key + * @return true : deleted, false : key is not found + * @throws JavetException the javet exception + * @since 2.2.0 */ - public void setGCScheduled(boolean gcScheduled) { - this.gcScheduled = gcScheduled; + @SuppressWarnings("RedundantThrows") + boolean setDelete(IV8ValueSet iV8ValueSet, V8Value key) throws JavetException { + return v8Native.setDelete(handle, iV8ValueSet.getHandle(), iV8ValueSet.getType().getId(), key); } /** - * Sets logger. + * Sets GC scheduled. * - * @param logger the logger + * @param gcScheduled the GC scheduled * @since 0.9.1 */ - public void setLogger(IJavetLogger logger) { - this.logger = logger; + public void setGCScheduled(boolean gcScheduled) { + this.gcScheduled = gcScheduled; } /** - * Sets a private property. + * Gets size from a set. * - * @param iV8ValueObject the V8 value object - * @param propertyName the property name - * @param propertyValue the property value - * @return true : success, false : failure + * @param iV8ValueSet the V8 value set + * @return the size * @throws JavetException the javet exception - * @since 0.9.12 + * @since 0.7.0 */ @SuppressWarnings("RedundantThrows") - boolean setPrivateProperty(IV8ValueObject iV8ValueObject, String propertyName, V8Value propertyValue) - throws JavetException { - return v8Native.setPrivateProperty( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), propertyName, propertyValue); + int setGetSize(IV8ValueSet iV8ValueSet) throws JavetException { + return v8Native.setGetSize(handle, iV8ValueSet.getHandle(), iV8ValueSet.getType().getId()); } /** - * Sets promise reject callback. + * Has a property in a set. * - * @param promiseRejectCallback the promise reject callback - * @since 0.9.1 + * @param iV8ValueSet the V8 value set + * @param value the value + * @return true : yes, false : no + * @throws JavetException the javet exception + * @since 2.2.0 */ - public void setPromiseRejectCallback(IJavetPromiseRejectCallback promiseRejectCallback) { - Objects.requireNonNull(promiseRejectCallback); - this.promiseRejectCallback = promiseRejectCallback; + @SuppressWarnings("RedundantThrows") + boolean setHas(IV8ValueSet iV8ValueSet, V8Value value) throws JavetException { + return v8Native.setHas(handle, iV8ValueSet.getHandle(), iV8ValueSet.getType().getId(), value); } /** - * Sets property. + * Sets logger. * - * @param iV8ValueObject the V8 value object - * @param key the key - * @param value the value - * @return true : success, false : failure - * @throws JavetException the javet exception - * @since 0.7.0 + * @param logger the logger + * @since 0.9.1 */ - @SuppressWarnings("RedundantThrows") - boolean setProperty(IV8ValueObject iV8ValueObject, V8Value key, V8Value value) throws JavetException { - return v8Native.setProperty(handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), key, value); + public void setLogger(IJavetLogger logger) { + this.logger = logger; } /** - * Sets prototype. + * Sets promise reject callback. * - * @param iV8ValueObject the V8 value object - * @param iV8ValueObjectPrototype the V8 value object prototype - * @return true : success, false : failure - * @throws JavetException the javet exception - * @since 0.9.4 + * @param promiseRejectCallback the promise reject callback + * @since 0.9.1 */ - @SuppressWarnings("RedundantThrows") - boolean setPrototype( - IV8ValueObject iV8ValueObject, IV8ValueObject iV8ValueObjectPrototype) - throws JavetException { - return v8Native.setPrototype( - handle, iV8ValueObject.getHandle(), iV8ValueObject.getType().getId(), - iV8ValueObjectPrototype.getHandle()); + public void setPromiseRejectCallback(IJavetPromiseRejectCallback promiseRejectCallback) { + Objects.requireNonNull(promiseRejectCallback); + this.promiseRejectCallback = promiseRejectCallback; } /** @@ -2685,19 +3305,6 @@ public T toObject(V v8Value) throws JavetException { return converter.toObject(v8Value); } - /** - * Gets a proto string from a reference. - * - * @param iV8ValueReference the V8 value reference - * @return the proto string - * @throws JavetException the javet exception - * @since 0.8.4 - */ - @SuppressWarnings("RedundantThrows") - String toProtoString(IV8ValueReference iV8ValueReference) throws JavetException { - return v8Native.toProtoString(handle, iV8ValueReference.getHandle(), iV8ValueReference.getType().getId()); - } - /** * Call toString(). * diff --git a/src/main/java/com/caoccao/javet/interop/callback/IJavetDirectCallable.java b/src/main/java/com/caoccao/javet/interop/callback/IJavetDirectCallable.java new file mode 100644 index 000000000..a5cdcebb5 --- /dev/null +++ b/src/main/java/com/caoccao/javet/interop/callback/IJavetDirectCallable.java @@ -0,0 +1,211 @@ +/* + * Copyright (c) 2021-2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interop.callback; + +import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.values.V8Value; + +import java.io.Serializable; + +/** + * The interface Javet direct callable is for converting the calls + * from reflection calls to direct calls. + * + * @since 2.2.0 + */ +public interface IJavetDirectCallable { + /** + * Get supported callback contexts. + * + * @return the supported callback contexts + * @since 2.2.0 + */ + JavetCallbackContext[] getCallbackContexts(); + + /** + * Sets V8 runtime. + * + * @param v8Runtime the V8 runtime + * @since 2.2.0 + */ + default void setV8Runtime(V8Runtime v8Runtime) { + // Pass. + } + + /** + * The interface Direct call. + * + * @since 2.2.0 + */ + interface DirectCall extends Serializable { + } + + /** + * The interface GetterAndNoThis gets the property value by a property key + * without this object passed in. + * + * @since 2.2.0 + */ + interface GetterAndNoThis extends DirectCall { + /** + * Get the property value by a property key + * without this object passed in. + * + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + V8Value get() throws JavetException, E; + } + + /** + * The interface GetterAndThis gets the property value by a property key + * with this object passed in. + * + * @since 2.2.0 + */ + interface GetterAndThis extends DirectCall { + /** + * Get the property value by a property key + * with this object passed in. + * + * @param thisObject the this object + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + V8Value get(V8Value thisObject) throws JavetException, E; + } + + /** + * The interface NoThisAndResult does not return the result and accept this object passed in. + * + * @since 2.2.0 + */ + interface NoThisAndNoResult extends DirectCall { + /** + * Call. + * + * @param v8Values the V8 values + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + void call(V8Value... v8Values) throws JavetException, E; + } + + /** + * The interface NoThisAndResult returns the result + * without this object passed in. + * + * @since 2.2.0 + */ + interface NoThisAndResult extends DirectCall { + /** + * Call and return the result. + * + * @param v8Values the V8 values + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + V8Value call(V8Value... v8Values) throws JavetException, E; + } + + /** + * The interface SetterAndNoThis gets the property value by a property key + * without this object passed in. + * + * @since 2.2.0 + */ + interface SetterAndNoThis extends DirectCall { + /** + * Set the property value by a property key + * without this object passed in. + * + * @param v8ValueValue the V8 value value + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + V8Value set(V8Value v8ValueValue) throws JavetException, E; + } + + /** + * The interface SetterAndThis gets the property value by a property key + * with this object passed in. + * + * @since 2.2.0 + */ + interface SetterAndThis extends DirectCall { + /** + * Set the property value by a property key + * with this object passed in. + * + * @param thisObject the this object + * @param v8ValueValue the V8 value value + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + V8Value set(V8Value thisObject, V8Value v8ValueValue) throws JavetException, E; + } + + /** + * The interface ThisAndNoResult does not return the result, but accepts this object. + * + * @since 2.2.0 + */ + interface ThisAndNoResult extends DirectCall { + /** + * Call by this object. + * + * @param thisObject the this object + * @param v8Values the V8 values + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + void call(V8Value thisObject, V8Value... v8Values) throws JavetException, E; + } + + /** + * The interface ThisAndResult accepts this object and returns the result. + * + * @param the custom exception + * @since 2.2.0 + */ + interface ThisAndResult extends DirectCall { + /** + * Call by this object and return the result. + * + * @param thisObject the this object + * @param v8Values the V8 values + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + V8Value call(V8Value thisObject, V8Value... v8Values) throws JavetException, E; + } +} diff --git a/src/main/java/com/caoccao/javet/interop/callback/JavetCallbackContext.java b/src/main/java/com/caoccao/javet/interop/callback/JavetCallbackContext.java index e5a3fcbce..5c23ca28e 100644 --- a/src/main/java/com/caoccao/javet/interop/callback/JavetCallbackContext.java +++ b/src/main/java/com/caoccao/javet/interop/callback/JavetCallbackContext.java @@ -16,6 +16,8 @@ package com.caoccao.javet.interop.callback; +import com.caoccao.javet.enums.V8ValueSymbolType; + import java.lang.reflect.Method; import java.lang.reflect.Modifier; import java.util.Objects; @@ -25,6 +27,7 @@ * * @since 0.7.1 */ +@SuppressWarnings("unchecked") public final class JavetCallbackContext { /** * The constant INVALID_HANDLE. @@ -34,53 +37,186 @@ public final class JavetCallbackContext { public static final long INVALID_HANDLE = 0L; private static final String ERROR_CALLBACK_RECEIVER_OR_CALLBACK_METHOD_IS_INVALID = "Callback receiver or callback method is invalid"; + private static final String ERROR_CALLBACK_TYPE_MISMATCHES = "Callback type mismatches."; private static final String ERROR_JAVET_CALLBACK_CONTEXT_HANDLE_IS_INVALID = "Javet callback context handle is invalid"; - private final Method callbackMethod; + private final Object callbackMethod; private final Object callbackReceiver; - private final boolean returnResult; + private final JavetCallbackType callbackType; + private final String name; + private final V8ValueSymbolType symbolType; private final boolean thisObjectRequired; private long handle; + private boolean returnResult; + + /** + * Instantiates a new Javet callback context. + * + * @param name the name + * @param callbackType the callback type + * @param directCall the direct call + * @since 2.2.0 + */ + public JavetCallbackContext( + String name, + JavetCallbackType callbackType, + IJavetDirectCallable.DirectCall directCall) { + this(name, V8ValueSymbolType.None, callbackType, directCall); + } /** * Instantiates a new Javet callback context. * + * @param name the name + * @param callbackReceiver the callback receiver + * @param callbackType the callback type + * @param directCall the direct call + * @since 2.2.0 + */ + public JavetCallbackContext( + String name, + Object callbackReceiver, + JavetCallbackType callbackType, + IJavetDirectCallable.DirectCall directCall) { + this(Objects.requireNonNull(name), V8ValueSymbolType.None, callbackReceiver, callbackType, directCall); + } + + /** + * Instantiates a new Javet callback context. + * + * @param name the name + * @param symbolType the symbol type + * @param callbackType the callback type + * @param directCall the direct call + * @since 2.2.0 + */ + public JavetCallbackContext( + String name, + V8ValueSymbolType symbolType, + JavetCallbackType callbackType, + IJavetDirectCallable.DirectCall directCall) { + this(Objects.requireNonNull(name), symbolType, null, callbackType, directCall); + } + + /** + * Instantiates a new Javet callback context that takes a Java method for making further reflection calls. + * + * @param name the name + * @param callbackReceiver the callback receiver + * @param callbackMethod the callback method + * @since 2.2.0 + */ + public JavetCallbackContext( + String name, + Object callbackReceiver, + Method callbackMethod) { + this(name, V8ValueSymbolType.None, callbackReceiver, callbackMethod); + } + + /** + * Instantiates a new Javet callback context that takes a Java method for making further reflection calls. + * + * @param name the name + * @param symbolType the symbol type * @param callbackReceiver the callback receiver * @param callbackMethod the callback method * @since 0.7.1 */ - public JavetCallbackContext(Object callbackReceiver, Method callbackMethod) { - this(callbackReceiver, callbackMethod, false); + public JavetCallbackContext( + String name, + V8ValueSymbolType symbolType, + Object callbackReceiver, + Method callbackMethod) { + this(name, symbolType, callbackReceiver, callbackMethod, false); } /** - * Instantiates a new Javet callback context. + * Instantiates a new Javet callback context that takes a Java method for making further reflection calls. * + * @param name the name + * @param callbackReceiver the callback receiver + * @param callbackMethod the callback method + * @param thisObjectRequired the this object required + * @since 2.2.0 + */ + public JavetCallbackContext( + String name, + Object callbackReceiver, + Method callbackMethod, + boolean thisObjectRequired) { + this(name, V8ValueSymbolType.None, callbackReceiver, callbackMethod, thisObjectRequired); + } + + /** + * Instantiates a new Javet callback context that takes a Java method for making further reflection calls. + * + * @param name the name + * @param symbolType the symbol type * @param callbackReceiver the callback receiver * @param callbackMethod the callback method * @param thisObjectRequired the this object required * @since 0.7.1 */ - public JavetCallbackContext(Object callbackReceiver, Method callbackMethod, boolean thisObjectRequired) { - Objects.requireNonNull(callbackMethod); + public JavetCallbackContext( + String name, + V8ValueSymbolType symbolType, + Object callbackReceiver, + Method callbackMethod, + boolean thisObjectRequired) { + this(Objects.requireNonNull(name), + symbolType, + callbackReceiver, + JavetCallbackType.Reflection, + callbackMethod, + thisObjectRequired); assert (callbackReceiver != null && !Modifier.isStatic(callbackMethod.getModifiers())) || (callbackReceiver == null && Modifier.isStatic(callbackMethod.getModifiers())) : ERROR_CALLBACK_RECEIVER_OR_CALLBACK_METHOD_IS_INVALID; - this.callbackMethod = callbackMethod; + this.returnResult = !callbackMethod.getReturnType().equals(Void.TYPE); + } + + private JavetCallbackContext( + String name, + V8ValueSymbolType symbolType, + Object callbackReceiver, + JavetCallbackType callbackType, + Object callbackMethod, + boolean thisObjectRequired) { + this.callbackMethod = Objects.requireNonNull(callbackMethod); this.callbackReceiver = callbackReceiver; + this.callbackType = Objects.requireNonNull(callbackType); handle = INVALID_HANDLE; - this.returnResult = !callbackMethod.getReturnType().equals(Void.TYPE); + this.name = name; this.thisObjectRequired = thisObjectRequired; + this.symbolType = Objects.requireNonNull(symbolType); + } + + private JavetCallbackContext( + String name, + V8ValueSymbolType symbolType, + Object callbackReceiver, + JavetCallbackType callbackType, + IJavetDirectCallable.DirectCall directCall) { + this( + name, + symbolType, + callbackReceiver, + Objects.requireNonNull(callbackType), + directCall, + callbackType.getThisObjectRequired()); + assert callbackType.getDirectCallClass().isAssignableFrom(directCall.getClass()) : ERROR_CALLBACK_TYPE_MISMATCHES; + this.returnResult = callbackType.getReturnResult(); } /** * Gets callback method. * + * @param the type parameter * @return the callback method * @since 0.9.1 */ - public Method getCallbackMethod() { - return callbackMethod; + public T getCallbackMethod() { + return (T) callbackMethod; } /** @@ -93,6 +229,16 @@ public Object getCallbackReceiver() { return callbackReceiver; } + /** + * Gets callback type. + * + * @return the callback type + * @since 2.2.0 + */ + public JavetCallbackType getCallbackType() { + return callbackType; + } + /** * Gets handle. * @@ -103,10 +249,24 @@ public long getHandle() { return handle; } + /** + * Gets name. + * + * @return the name + * @since 2.2.0 + */ + public String getName() { + return name; + } + + public V8ValueSymbolType getSymbolType() { + return symbolType; + } + /** * Is return result. * - * @return the boolean + * @return true : yes, false : no * @since 0.9.1 */ public boolean isReturnResult() { @@ -116,7 +276,7 @@ public boolean isReturnResult() { /** * Is this object required. * - * @return the boolean + * @return true : yes, false : no * @since 0.9.1 */ public boolean isThisObjectRequired() { @@ -126,7 +286,7 @@ public boolean isThisObjectRequired() { /** * Is valid. * - * @return the boolean + * @return true : yes, false : no * @since 0.9.11 */ public boolean isValid() { @@ -139,7 +299,7 @@ public boolean isValid() { * @param handle the handle * @since 0.7.1 */ - public void setHandle(long handle) { + void setHandle(long handle) { assert !isValid() : ERROR_JAVET_CALLBACK_CONTEXT_HANDLE_IS_INVALID; this.handle = handle; } diff --git a/src/main/java/com/caoccao/javet/interop/callback/JavetCallbackType.java b/src/main/java/com/caoccao/javet/interop/callback/JavetCallbackType.java new file mode 100644 index 000000000..714b1a42e --- /dev/null +++ b/src/main/java/com/caoccao/javet/interop/callback/JavetCallbackType.java @@ -0,0 +1,124 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interop.callback; + +/** + * The enum Javet callback type. + * + * @since 2.2.0 + */ +public enum JavetCallbackType { + /** + * The callback is via Java direct getter without this object. + * + * @since 2.2.0 + */ + DirectCallGetterAndNoThis(IJavetDirectCallable.GetterAndNoThis.class, false, true), + /** + * The callback is via Java direct getter with this object. + * + * @since 2.2.0 + */ + DirectCallGetterAndThis(IJavetDirectCallable.GetterAndThis.class, true, true), + /** + * The callback is via Java direct setter without this object. + * + * @since 2.2.0 + */ + DirectCallSetterAndNoThis(IJavetDirectCallable.SetterAndNoThis.class, false, true), + /** + * The callback is via Java direct setter with this object. + * + * @since 2.2.0 + */ + DirectCallSetterAndThis(IJavetDirectCallable.SetterAndThis.class, true, true), + /** + * The callback is via Java direct call without this object and without result. + * + * @since 2.2.0 + */ + DirectCallNoThisAndNoResult(IJavetDirectCallable.NoThisAndNoResult.class, false, false), + /** + * The callback is via Java direct call without this object and with result. + * + * @since 2.2.0 + */ + DirectCallNoThisAndResult(IJavetDirectCallable.NoThisAndResult.class, false, true), + /** + * The callback is via Java direct call with this object and without result. + * + * @since 2.2.0 + */ + DirectCallThisAndNoResult(IJavetDirectCallable.ThisAndNoResult.class, true, false), + /** + * The callback is via Java direct call with this object and with result. + * + * @since 2.2.0 + */ + DirectCallThisAndResult(IJavetDirectCallable.ThisAndResult.class, true, true), + /** + * The callback is via Java reflection. + *

    + * PROS: It's non-intrusive and supports all kinds of Java classes. + * CONS: Performance is relatively low. + * + * @since 2.2.0 + */ + Reflection(null, null, null); + private final Class directCallClass; + private final Boolean returnResult; + private final Boolean thisObjectRequired; + + JavetCallbackType( + Class directCallClass, + Boolean thisObjectRequired, + Boolean returnResult) { + this.directCallClass = directCallClass; + this.returnResult = returnResult; + this.thisObjectRequired = thisObjectRequired; + } + + /** + * Gets direct call class. + * + * @return the direct call class + * @since 2.2.0 + */ + public Class getDirectCallClass() { + return directCallClass; + } + + /** + * Gets return result. + * + * @return the return result + * @since 2.2.0 + */ + public Boolean getReturnResult() { + return returnResult; + } + + /** + * Gets this object required. + * + * @return the this object required + * @since 2.2.0 + */ + public Boolean getThisObjectRequired() { + return thisObjectRequired; + } +} diff --git a/src/main/java/com/caoccao/javet/interop/callback/V8FunctionCallback.java b/src/main/java/com/caoccao/javet/interop/callback/V8FunctionCallback.java index fb1cf258e..bd74dd4cf 100644 --- a/src/main/java/com/caoccao/javet/interop/callback/V8FunctionCallback.java +++ b/src/main/java/com/caoccao/javet/interop/callback/V8FunctionCallback.java @@ -27,7 +27,6 @@ import com.caoccao.javet.utils.SimpleMap; import com.caoccao.javet.values.IV8Value; import com.caoccao.javet.values.V8Value; -import com.caoccao.javet.values.reference.V8ValueArray; import java.lang.reflect.Array; import java.lang.reflect.InvocationTargetException; @@ -304,7 +303,7 @@ private static Object convert(IJavetConverter converter, Class expectedClass, } /** - * Receive callback V8 value. + * Receive callback and return the V8 value. * * @param v8Runtime the V8 runtime * @param javetCallbackContext the javet callback context @@ -318,9 +317,8 @@ public static V8Value receiveCallback( V8Runtime v8Runtime, JavetCallbackContext javetCallbackContext, V8Value thisObject, - V8ValueArray args) throws Throwable { + V8Value[] args) throws Throwable { if (javetCallbackContext != null) { - List values = new ArrayList<>(); Object resultObject = null; try { /* @@ -330,63 +328,127 @@ public static V8Value receiveCallback( * to the receiver so that the receiver can create reference V8Value. */ IJavetConverter converter = v8Runtime.getConverter(); - /* - * Javet doesn't check whether callback method is static or not. - * If the callback receiver is null, that's a static method. - */ - Method method = javetCallbackContext.getCallbackMethod(); - JavetReflectionUtils.safeSetAccessible(method); - Object callbackReceiver = javetCallbackContext.getCallbackReceiver(); - if (javetCallbackContext.isThisObjectRequired()) { - values.add(thisObject); - } - if (args != null) { - final int length = args.getLength(); - for (int i = 0; i < length; ++i) { - values.add(args.get(i)); + if (javetCallbackContext.getCallbackType() == JavetCallbackType.Reflection) { + /* + * Javet doesn't check whether callback method is static or not. + * If the callback receiver is null, that's a static method. + */ + Method method = javetCallbackContext.getCallbackMethod(); + JavetReflectionUtils.safeSetAccessible(method); + Object callbackReceiver = javetCallbackContext.getCallbackReceiver(); + List values = new ArrayList<>(); + if (javetCallbackContext.isThisObjectRequired()) { + values.add(thisObject); } - } - if (values.isEmpty()) { - if (method.isVarArgs()) { - Class[] parameterTypes = method.getParameterTypes(); - Class parameterClass = parameterTypes[parameterTypes.length - 1]; - Object varObject = Array.newInstance(parameterClass.getComponentType(), 0); - resultObject = method.invoke(callbackReceiver, varObject); - } else { - resultObject = method.invoke(callbackReceiver); + if (args != null && args.length > 0) { + Collections.addAll(values, args); } - } else { - final int length = values.size(); - List objectValues = new ArrayList<>(); - Class[] parameterTypes = method.getParameterTypes(); - if (method.isVarArgs()) { - for (int i = 0; i < parameterTypes.length; ++i) { - Class parameterClass = parameterTypes[i]; - if (parameterClass.isArray() && i == parameterTypes.length - 1) { - // VarArgs is special. It requires special API to manipulate the array. - Class componentType = parameterClass.getComponentType(); - Object varObject = Array.newInstance(componentType, length - i); - for (int j = i; j < length; ++j) { - Array.set(varObject, j - i, - convert(converter, componentType, (V8Value) values.get(j))); - } - objectValues.add(varObject); - } else { - objectValues.add(convert(converter, parameterClass, (V8Value) values.get(i))); - } + if (values.isEmpty()) { + if (method.isVarArgs()) { + Class[] parameterTypes = method.getParameterTypes(); + Class parameterClass = parameterTypes[parameterTypes.length - 1]; + Object varObject = Array.newInstance(parameterClass.getComponentType(), 0); + resultObject = method.invoke(callbackReceiver, varObject); + } else { + resultObject = method.invoke(callbackReceiver); } } else { - for (int i = 0; i < parameterTypes.length; ++i) { - /* - * Virtual varargs support. - * Redundant parameters will be dropped. - * Absent parameters will be filled by the default values. - */ - V8Value v8Value = i < length ? (V8Value) values.get(i) : null; - objectValues.add(convert(converter, parameterTypes[i], v8Value)); + final int length = values.size(); + List objectValues = new ArrayList<>(); + Class[] parameterTypes = method.getParameterTypes(); + if (method.isVarArgs()) { + for (int i = 0; i < parameterTypes.length; ++i) { + Class parameterClass = parameterTypes[i]; + if (parameterClass.isArray() && i == parameterTypes.length - 1) { + // VarArgs is special. It requires special API to manipulate the array. + Class componentType = parameterClass.getComponentType(); + Object varObject = Array.newInstance(componentType, length - i); + for (int j = i; j < length; ++j) { + Array.set(varObject, j - i, + convert(converter, componentType, (V8Value) values.get(j))); + } + objectValues.add(varObject); + } else { + objectValues.add(convert(converter, parameterClass, (V8Value) values.get(i))); + } + } + } else { + for (int i = 0; i < parameterTypes.length; ++i) { + /* + * Virtual varargs support. + * Redundant parameters will be dropped. + * Absent parameters will be filled by the default values. + */ + V8Value v8Value = i < length ? (V8Value) values.get(i) : null; + objectValues.add(convert(converter, parameterTypes[i], v8Value)); + } } + resultObject = method.invoke(callbackReceiver, objectValues.toArray()); + } + } else { + switch (javetCallbackContext.getCallbackType()) { + case DirectCallGetterAndNoThis: + IJavetDirectCallable.GetterAndNoThis directCallGetterAndNoThis = + javetCallbackContext.getCallbackMethod(); + resultObject = directCallGetterAndNoThis.get(); + break; + case DirectCallGetterAndThis: + IJavetDirectCallable.GetterAndThis directCallGetterAndThis = + javetCallbackContext.getCallbackMethod(); + resultObject = directCallGetterAndThis.get(thisObject); + break; + case DirectCallSetterAndNoThis: + IJavetDirectCallable.SetterAndNoThis directCallSetterAndNoThis = + javetCallbackContext.getCallbackMethod(); + if (args == null || args.length < 1) { + throw new JavetException(JavetError.CallbackSignatureParameterSizeMismatch, + SimpleMap.of( + JavetError.PARAMETER_METHOD_NAME, + javetCallbackContext.getName(), + JavetError.PARAMETER_EXPECTED_PARAMETER_SIZE, 1, + JavetError.PARAMETER_ACTUAL_PARAMETER_SIZE, args == null ? 0 : args.length)); + } + directCallSetterAndNoThis.set(args[0]); + break; + case DirectCallSetterAndThis: + IJavetDirectCallable.SetterAndThis directCallSetterAndThis = + javetCallbackContext.getCallbackMethod(); + if (args == null || args.length != 1) { + throw new JavetException(JavetError.CallbackSignatureParameterSizeMismatch, + SimpleMap.of( + JavetError.PARAMETER_METHOD_NAME, + javetCallbackContext.getName(), + JavetError.PARAMETER_EXPECTED_PARAMETER_SIZE, 1, + JavetError.PARAMETER_ACTUAL_PARAMETER_SIZE, args == null ? 0 : args.length)); + } + directCallSetterAndThis.set(thisObject, args[0]); + break; + case DirectCallThisAndNoResult: + IJavetDirectCallable.ThisAndNoResult directCallThisAndNoResult = + javetCallbackContext.getCallbackMethod(); + directCallThisAndNoResult.call(thisObject, args); + break; + case DirectCallThisAndResult: + IJavetDirectCallable.ThisAndResult directCallThisAndResult = + javetCallbackContext.getCallbackMethod(); + resultObject = directCallThisAndResult.call(thisObject, args); + break; + case DirectCallNoThisAndNoResult: + IJavetDirectCallable.NoThisAndNoResult directCallNoThisAndNoResult = + javetCallbackContext.getCallbackMethod(); + directCallNoThisAndNoResult.call(args); + break; + case DirectCallNoThisAndResult: + IJavetDirectCallable.NoThisAndResult directCallNoThisAndResult = + javetCallbackContext.getCallbackMethod(); + resultObject = directCallNoThisAndResult.call(args); + break; + default: + throw new JavetException(JavetError.CallbackTypeNotSupported, + SimpleMap.of( + JavetError.PARAMETER_CALLBACK_TYPE, + javetCallbackContext.getCallbackType().name())); } - resultObject = method.invoke(callbackReceiver, objectValues.toArray()); } if (javetCallbackContext.isReturnResult()) { if (!(resultObject instanceof IV8Value)) { @@ -402,17 +464,16 @@ public static V8Value receiveCallback( throw e.getTargetException(); } finally { // Result object must be excluded because it will be closed in JNI. - if (!javetCallbackContext.isThisObjectRequired()) { + if (javetCallbackContext.isThisObjectRequired()) { if (thisObject != resultObject) { JavetResourceUtils.safeClose(thisObject); } } - if (args != resultObject) { - JavetResourceUtils.safeClose(args); - } - for (Object value : values) { - if (value != resultObject) { - JavetResourceUtils.safeClose(value); + if (args != null) { + for (V8Value value : args) { + if (value != resultObject) { + JavetResourceUtils.safeClose(value); + } } } } diff --git a/src/main/java/com/caoccao/javet/interop/converters/JavetConverterConfig.java b/src/main/java/com/caoccao/javet/interop/converters/JavetConverterConfig.java index a0bfa07a4..a76c7fcef 100644 --- a/src/main/java/com/caoccao/javet/interop/converters/JavetConverterConfig.java +++ b/src/main/java/com/caoccao/javet/interop/converters/JavetConverterConfig.java @@ -16,7 +16,7 @@ package com.caoccao.javet.interop.converters; -import com.caoccao.javet.interop.proxy.IJavetDynamicObjectFactory; +import com.caoccao.javet.interop.proxy.IJavetReflectionObjectFactory; /** * The type Javet converter config. @@ -79,12 +79,6 @@ public class JavetConverterConfig> { * @since 0.9.4 */ protected short defaultShort; - /** - * The Dynamic object factory. - * - * @since 2.0.1 - */ - protected IJavetDynamicObjectFactory dynamicObjectFactory; /** * The Extract function source code. * @@ -109,6 +103,12 @@ public class JavetConverterConfig> { * @since 0.9.8 */ protected boolean proxySetEnabled; + /** + * The Reflection object factory. + * + * @since 2.0.1 + */ + protected IJavetReflectionObjectFactory reflectionObjectFactory; /** * This flag determines whether function should be skipped in object or not. * @@ -130,7 +130,7 @@ public JavetConverterConfig() { defaultInt = 0; defaultLong = 0L; defaultShort = 0; - dynamicObjectFactory = null; + reflectionObjectFactory = null; extractFunctionSourceCode = false; maxDepth = DEFAULT_MAX_DEPTH; proxyMapEnabled = false; @@ -217,10 +217,6 @@ public short getDefaultShort() { return defaultShort; } - public IJavetDynamicObjectFactory getDynamicObjectFactory() { - return dynamicObjectFactory; - } - /** * Gets max depth. * @@ -231,6 +227,16 @@ public int getMaxDepth() { return maxDepth; } + /** + * Gets reflection object factory. + * + * @return the reflection object factory + * @since 2.0.1 + */ + public IJavetReflectionObjectFactory getReflectionObjectFactory() { + return reflectionObjectFactory; + } + /** * Is extract function source code boolean. * @@ -375,10 +381,6 @@ public JavetConverterConfig setDefaultShort(short defaultShort) { return this; } - public void setDynamicObjectFactory(IJavetDynamicObjectFactory dynamicObjectFactory) { - this.dynamicObjectFactory = dynamicObjectFactory; - } - /** * Sets extract function source code. * @@ -431,6 +433,19 @@ public JavetConverterConfig setProxySetEnabled(boolean proxySetEnabled) { return this; } + /** + * Sets reflection object factory. + * + * @param reflectionObjectFactory the reflection object factory + * @return the self + * @since 2.0.1 + */ + @SuppressWarnings("UnusedReturnValue") + public JavetConverterConfig setReflectionObjectFactory(IJavetReflectionObjectFactory reflectionObjectFactory) { + this.reflectionObjectFactory = reflectionObjectFactory; + return this; + } + /** * Sets skip functions. * diff --git a/src/main/java/com/caoccao/javet/interop/converters/JavetObjectConverter.java b/src/main/java/com/caoccao/javet/interop/converters/JavetObjectConverter.java index 27a6d2efc..2a58654d4 100644 --- a/src/main/java/com/caoccao/javet/interop/converters/JavetObjectConverter.java +++ b/src/main/java/com/caoccao/javet/interop/converters/JavetObjectConverter.java @@ -28,7 +28,8 @@ import com.caoccao.javet.interop.V8Scope; import com.caoccao.javet.interop.callback.JavetCallbackContext; import com.caoccao.javet.interop.proxy.IJavetProxyHandler; -import com.caoccao.javet.interop.proxy.JavetDynamicProxyObjectHandler; +import com.caoccao.javet.interop.proxy.JavetReflectionProxyObjectHandler; +import com.caoccao.javet.utils.JavetResourceUtils; import com.caoccao.javet.values.V8Value; import com.caoccao.javet.values.reference.*; @@ -264,8 +265,8 @@ protected T toObject(V8Value v8Value, final int depth) throws JavetException if (handle != null) { JavetCallbackContext javetCallbackContext = v8ValueProxy.getV8Runtime().getCallbackContext(handle); if (javetCallbackContext != null) { - IJavetProxyHandler iJavetProxyHandler = - (IJavetProxyHandler) javetCallbackContext.getCallbackReceiver(); + IJavetProxyHandler iJavetProxyHandler = + (IJavetProxyHandler) javetCallbackContext.getCallbackReceiver(); Object targetObject = iJavetProxyHandler.getTargetObject(); if (targetObject != null) { return (T) targetObject; @@ -341,9 +342,8 @@ protected T toV8Value( try (V8Scope v8Scope = v8Runtime.getV8Scope()) { V8ValueProxy v8ValueProxy = v8Scope.createV8ValueProxy(); try (IV8ValueObject iV8ValueObjectHandler = v8ValueProxy.getHandler()) { - JavetDynamicProxyObjectHandler> javetProxyHandler = - new JavetDynamicProxyObjectHandler<>( - v8Runtime, null, (Map) object); + JavetReflectionProxyObjectHandler, ?> javetProxyHandler = + new JavetReflectionProxyObjectHandler<>(v8Runtime, null, (Map) object); List javetCallbackContexts = iV8ValueObjectHandler.bind(javetProxyHandler); iV8ValueObjectHandler.setPrivateProperty( @@ -371,9 +371,8 @@ protected T toV8Value( try (V8Scope v8Scope = v8Runtime.getV8Scope()) { V8ValueProxy v8ValueProxy = v8Scope.createV8ValueProxy(); try (IV8ValueObject iV8ValueObjectHandler = v8ValueProxy.getHandler()) { - JavetDynamicProxyObjectHandler> javetProxyHandler = - new JavetDynamicProxyObjectHandler<>( - v8Runtime, null, (Set) object); + JavetReflectionProxyObjectHandler, ?> javetProxyHandler = + new JavetReflectionProxyObjectHandler<>(v8Runtime, null, (Set) object); List javetCallbackContexts = iV8ValueObjectHandler.bind(javetProxyHandler); iV8ValueObjectHandler.setPrivateProperty( @@ -397,26 +396,46 @@ protected T toV8Value( } } else if (object instanceof Collection) { try (V8Scope v8Scope = v8Runtime.getV8Scope()) { - V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); - for (Object item : (Collection) object) { - try (V8Value childV8Value = toV8Value(v8Runtime, item, depth + 1)) { - v8ValueArray.push(childV8Value); + Collection list = (Collection) object; + V8Value[] childV8Values = null; + try { + if (!list.isEmpty()) { + childV8Values = new V8Value[list.size()]; + int i = 0; + for (Object item : list) { + childV8Values[i] = toV8Value(v8Runtime, item, depth + 1); + ++i; + } + } + V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); + if (childV8Values != null) { + v8ValueArray.push((Object[]) childV8Values); + } + v8Value = v8ValueArray; + v8Scope.setEscapable(); + } finally { + if (childV8Values != null) { + JavetResourceUtils.safeClose(childV8Values); } } - v8Value = v8ValueArray; - v8Scope.setEscapable(); } } else if (object instanceof BaseStream) { try (V8Scope v8Scope = v8Runtime.getV8Scope()) { - V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); final Iterator iterator = ((BaseStream) object).iterator(); - while (iterator.hasNext()) { - try (V8Value childV8Value = toV8Value(v8Runtime, iterator.next(), depth + 1)) { - v8ValueArray.push(childV8Value); + List childV8Values = new ArrayList<>(); + try { + while (iterator.hasNext()) { + childV8Values.add(toV8Value(v8Runtime, iterator.next(), depth + 1)); + } + V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); + if (!childV8Values.isEmpty()) { + v8ValueArray.push(childV8Values.toArray()); } + v8Value = v8ValueArray; + v8Scope.setEscapable(); + } finally { + JavetResourceUtils.safeClose(childV8Values); } - v8Value = v8ValueArray; - v8Scope.setEscapable(); } } else if (object instanceof IJavetEntityFunction) { final IJavetEntityFunction javetEntityFunction = (IJavetEntityFunction) object; @@ -433,11 +452,25 @@ protected T toV8Value( } else if (object.getClass().isArray()) { try (V8Scope v8Scope = v8Runtime.getV8Scope()) { if (object instanceof boolean[]) { - V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); - for (boolean item : (boolean[]) object) { - v8ValueArray.push(v8Runtime.createV8ValueBoolean(item)); + boolean[] booleans = (boolean[]) object; + V8Value[] childV8Values = null; + try { + if (booleans.length > 0) { + childV8Values = new V8Value[booleans.length]; + for (int i = 0; i < booleans.length; i++) { + childV8Values[i] = v8Runtime.createV8ValueBoolean(booleans[i]); + } + } + V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); + if (childV8Values != null) { + v8ValueArray.push((Object[]) childV8Values); + } + v8Value = v8ValueArray; + } finally { + if (childV8Values != null) { + JavetResourceUtils.safeClose(childV8Values); + } } - v8Value = v8ValueArray; } else if (object instanceof byte[]) { byte[] bytes = (byte[]) object; V8ValueTypedArray v8ValueTypedArray = v8Scope.createV8ValueTypedArray( @@ -445,11 +478,25 @@ protected T toV8Value( v8ValueTypedArray.fromBytes(bytes); v8Value = v8ValueTypedArray; } else if (object instanceof char[]) { - V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); - for (char c : (char[]) object) { - v8ValueArray.push(Character.toString(c)); + char[] chars = (char[]) object; + V8Value[] childV8Values = null; + try { + if (chars.length > 0) { + childV8Values = new V8Value[chars.length]; + for (int i = 0; i < chars.length; i++) { + childV8Values[i] = v8Runtime.createV8ValueString(Character.toString(chars[i])); + } + } + V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); + if (childV8Values != null) { + v8ValueArray.push((Object[]) childV8Values); + } + v8Value = v8ValueArray; + } finally { + if (childV8Values != null) { + JavetResourceUtils.safeClose(childV8Values); + } } - v8Value = v8ValueArray; } else if (object instanceof double[]) { double[] doubles = (double[]) object; V8ValueTypedArray v8ValueTypedArray = v8Scope.createV8ValueTypedArray( @@ -481,19 +528,45 @@ protected T toV8Value( v8ValueTypedArray.fromShorts(shorts); v8Value = v8ValueTypedArray; } else if (object instanceof String[]) { - V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); - for (String item : (String[]) object) { - v8ValueArray.push(v8Runtime.createV8ValueString(item)); + String[] strings = (String[]) object; + V8Value[] childV8Values = null; + try { + if (strings.length > 0) { + childV8Values = new V8Value[strings.length]; + for (int i = 0; i < strings.length; i++) { + childV8Values[i] = v8Runtime.createV8ValueString(strings[i]); + } + } + V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); + if (childV8Values != null) { + v8ValueArray.push((Object[]) childV8Values); + } + v8Value = v8ValueArray; + } finally { + if (childV8Values != null) { + JavetResourceUtils.safeClose(childV8Values); + } } - v8Value = v8ValueArray; } else { - V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); - for (Object item : (Object[]) object) { - try (V8Value childV8Value = toV8Value(v8Runtime, item, depth + 1)) { - v8ValueArray.push(childV8Value); + Object[] objects = (Object[]) object; + V8Value[] childV8Values = null; + try { + if (objects.length > 0) { + childV8Values = new V8Value[objects.length]; + for (int i = 0; i < objects.length; i++) { + childV8Values[i] = toV8Value(v8Runtime, objects[i], depth + 1); + } + } + V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); + if (childV8Values != null) { + v8ValueArray.push((Object[]) childV8Values); + } + v8Value = v8ValueArray; + } finally { + if (childV8Values != null) { + JavetResourceUtils.safeClose(childV8Values); } } - v8Value = v8ValueArray; } v8Scope.setEscapable(); } diff --git a/src/main/java/com/caoccao/javet/interop/converters/JavetProxyConverter.java b/src/main/java/com/caoccao/javet/interop/converters/JavetProxyConverter.java index 85fcd4c81..e3ff5fc0c 100644 --- a/src/main/java/com/caoccao/javet/interop/converters/JavetProxyConverter.java +++ b/src/main/java/com/caoccao/javet/interop/converters/JavetProxyConverter.java @@ -23,10 +23,7 @@ import com.caoccao.javet.interop.V8Runtime; import com.caoccao.javet.interop.V8Scope; import com.caoccao.javet.interop.callback.JavetCallbackContext; -import com.caoccao.javet.interop.proxy.IJavetProxyHandler; -import com.caoccao.javet.interop.proxy.JavetDynamicProxyClassHandler; -import com.caoccao.javet.interop.proxy.JavetDynamicProxyFunctionHandler; -import com.caoccao.javet.interop.proxy.JavetDynamicProxyObjectHandler; +import com.caoccao.javet.interop.proxy.*; import com.caoccao.javet.values.V8Value; import com.caoccao.javet.values.primitive.V8ValueLong; import com.caoccao.javet.values.reference.IV8ValueObject; @@ -108,19 +105,29 @@ protected T toProxiedV8Value(V8Runtime v8Runtime, Object obj break; } try (IV8ValueObject iV8ValueObjectHandler = v8ValueProxy.getHandler()) { - IJavetProxyHandler javetProxyHandler; + IJavetProxyHandler javetProxyHandler; switch (proxyMode) { case Class: - javetProxyHandler = new JavetDynamicProxyClassHandler<>( - v8Runtime, config.getDynamicObjectFactory(), (Class) object); + javetProxyHandler = new JavetReflectionProxyClassHandler<>( + v8Runtime, config.getReflectionObjectFactory(), (Class) object); break; case Function: - javetProxyHandler = new JavetDynamicProxyFunctionHandler<>( - v8Runtime, config.getDynamicObjectFactory(), object); + if (object instanceof IJavetDirectProxyHandler) { + javetProxyHandler = new JavetDirectProxyFunctionHandler<>( + v8Runtime, (IJavetDirectProxyHandler) object); + } else { + javetProxyHandler = new JavetReflectionProxyFunctionHandler<>( + v8Runtime, config.getReflectionObjectFactory(), object); + } break; default: - javetProxyHandler = new JavetDynamicProxyObjectHandler<>( - v8Runtime, config.getDynamicObjectFactory(), object); + if (object instanceof IJavetDirectProxyHandler) { + javetProxyHandler = new JavetDirectProxyObjectHandler<>( + v8Runtime, (IJavetDirectProxyHandler) object); + } else { + javetProxyHandler = new JavetReflectionProxyObjectHandler<>( + v8Runtime, config.getReflectionObjectFactory(), object); + } break; } List javetCallbackContexts = iV8ValueObjectHandler.bind(javetProxyHandler); diff --git a/src/main/java/com/caoccao/javet/interop/loader/JavetLibLoader.java b/src/main/java/com/caoccao/javet/interop/loader/JavetLibLoader.java index b213c9736..42ba32636 100644 --- a/src/main/java/com/caoccao/javet/interop/loader/JavetLibLoader.java +++ b/src/main/java/com/caoccao/javet/interop/loader/JavetLibLoader.java @@ -48,7 +48,7 @@ public final class JavetLibLoader { * * @since 0.8.0 */ - public static final String LIB_VERSION = "2.1.2"; + public static final String LIB_VERSION = "2.2.0"; private static final String ANDROID_ABI_ARM = "armeabi-v7a"; private static final String ANDROID_ABI_ARM64 = "arm64-v8a"; private static final String ANDROID_ABI_X86 = "x86"; diff --git a/src/main/java/com/caoccao/javet/interop/options/RuntimeOptions.java b/src/main/java/com/caoccao/javet/interop/options/RuntimeOptions.java index 567dc2b35..30d0cd9fc 100644 --- a/src/main/java/com/caoccao/javet/interop/options/RuntimeOptions.java +++ b/src/main/java/com/caoccao/javet/interop/options/RuntimeOptions.java @@ -16,7 +16,7 @@ package com.caoccao.javet.interop.options; -import com.caoccao.javet.interop.proxy.IJavetDynamicObjectFactory; +import com.caoccao.javet.interop.proxy.IJavetReflectionObjectFactory; /** * The type Runtime options. @@ -26,11 +26,11 @@ */ public abstract class RuntimeOptions> { /** - * The dynamic object factory. + * The reflection object factory. * * @since 2.0.1 */ - protected IJavetDynamicObjectFactory dynamicObjectFactory; + protected IJavetReflectionObjectFactory reflectionObjectFactory; /** * Instantiates a new Runtime options. @@ -38,28 +38,28 @@ public abstract class RuntimeOptions> { * @since 1.0.0 */ public RuntimeOptions() { - dynamicObjectFactory = null; + reflectionObjectFactory = null; } /** - * Gets dynamic object factory. + * Gets reflection object factory. * - * @return the dynamic object factory + * @return the reflection object factory * @since 2.0.1 */ - public IJavetDynamicObjectFactory getDynamicObjectFactory() { - return dynamicObjectFactory; + public IJavetReflectionObjectFactory getReflectionObjectFactory() { + return reflectionObjectFactory; } /** - * Sets dynamic object factory. + * Sets reflection object factory. * - * @param dynamicObjectFactory the dynamic object factory + * @param reflectionObjectFactory the reflection object factory * @return the self * @since 2.0.1 */ - public RuntimeOptions setDynamicObjectFactory(IJavetDynamicObjectFactory dynamicObjectFactory) { - this.dynamicObjectFactory = dynamicObjectFactory; + public RuntimeOptions setReflectionObjectFactory(IJavetReflectionObjectFactory reflectionObjectFactory) { + this.reflectionObjectFactory = reflectionObjectFactory; return this; } } diff --git a/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetDirectProxyHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetDirectProxyHandler.java new file mode 100644 index 000000000..f8d32b56b --- /dev/null +++ b/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetDirectProxyHandler.java @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interop.proxy; + +import com.caoccao.javet.interop.V8Runtime; + +/** + * The type Base javet direct proxy handler. + * + * @param the type parameter + * @param the type parameter + * @since 2.2.0 + */ +public abstract class BaseJavetDirectProxyHandler, E extends Exception> + extends BaseJavetProxyHandler { + /** + * Instantiates a new Base javet direct proxy handler. + * + * @param v8Runtime the V8 runtime + * @param targetObject the target object + * @since 2.2.0 + */ + public BaseJavetDirectProxyHandler(V8Runtime v8Runtime, T targetObject) { + super(v8Runtime, targetObject); + targetObject.setV8Runtime(v8Runtime); + } +} diff --git a/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetProxyHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetProxyHandler.java index 68802cf45..b23214945 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetProxyHandler.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetProxyHandler.java @@ -1,736 +1,75 @@ -/* - * Copyright (c) 2021-2023. caoccao.com Sam Cao - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.caoccao.javet.interop.proxy; - -import com.caoccao.javet.annotations.*; -import com.caoccao.javet.enums.V8ConversionMode; -import com.caoccao.javet.exceptions.JavetError; -import com.caoccao.javet.exceptions.JavetException; -import com.caoccao.javet.interop.V8Runtime; -import com.caoccao.javet.interop.binding.ClassDescriptor; -import com.caoccao.javet.utils.*; -import com.caoccao.javet.values.V8Value; -import com.caoccao.javet.values.primitive.V8ValueString; -import com.caoccao.javet.values.reference.V8ValueObject; - -import java.lang.reflect.*; -import java.util.*; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - -/** - * The type Base javet proxy handler. - * - * @param the type parameter - * @since 0.9.6 - */ -public abstract class BaseJavetProxyHandler implements IJavetProxyHandler { - - /** - * The constant FUNCTION_NAME_TO_V8_VALUE. - * - * @since 1.0.4 - */ - public static final String FUNCTION_NAME_TO_V8_VALUE = "toV8Value"; - /** - * The constant GETTER_PREFIX_ARRAY. - * - * @since 0.9.6 - */ - protected static final String[] GETTER_PREFIX_ARRAY = new String[]{"get", "is"}; - /** - * The constant PATTERN_CAPITALIZED_PREFIX. - * - * @since 0.9.7 - */ - protected static final Pattern PATTERN_CAPITALIZED_PREFIX = Pattern.compile("^[A-Z]+"); - /** - * The constant SETTER_PREFIX_ARRAY. - * - * @since 0.9.6 - */ - protected static final String[] SETTER_PREFIX_ARRAY = new String[]{"set", "put"}; - /** - * The Class descriptor. - * - * @since 1.1.7 - */ - protected ClassDescriptor classDescriptor; - /** - * The dynamic object factory. - * - * @since 2.0.1 - */ - protected IJavetDynamicObjectFactory dynamicObjectFactory; - /** - * The Target object. - * - * @since 0.9.6 - */ - protected T targetObject; - /** - * The V8 runtime. - * - * @since 0.9.6 - */ - protected V8Runtime v8Runtime; - - /** - * Instantiates a new Base javet proxy handler. - * - * @param v8Runtime the V8 runtime - * @param dynamicObjectFactory the javet dynamic object factory - * @param targetObject the target object - * @since 0.9.6 - */ - public BaseJavetProxyHandler( - V8Runtime v8Runtime, - IJavetDynamicObjectFactory dynamicObjectFactory, - T targetObject) { - this.dynamicObjectFactory = dynamicObjectFactory; - this.targetObject = targetObject; - this.v8Runtime = Objects.requireNonNull(v8Runtime); - initialize(); - } - - /** - * Execute. - * - * @param the type parameter - * @param dynamicObjectFactory the dynamic object factory - * @param targetObject the target object - * @param thisObject this object - * @param executables the executables - * @param javetVirtualObjects the javet virtual objects - * @return the object - * @throws Throwable the throwable - * @since 0.9.10 - */ - protected static Object execute( - IJavetDynamicObjectFactory dynamicObjectFactory, - Object targetObject, - V8ValueObject thisObject, - List executables, - JavetVirtualObject[] javetVirtualObjects) throws Throwable { - List> scoredExecutables = new ArrayList<>(); - for (E executable : executables) { - ScoredExecutable scoredExecutable = new ScoredExecutable<>( - dynamicObjectFactory, targetObject, thisObject, executable, javetVirtualObjects); - scoredExecutable.calculateScore(); - double score = scoredExecutable.getScore(); - if (score > 0) { - scoredExecutables.add(scoredExecutable); - } - } - if (!scoredExecutables.isEmpty()) { - scoredExecutables.sort((o1, o2) -> Double.compare(o2.getScore(), o1.getScore())); - Throwable lastException = null; - for (ScoredExecutable scoredExecutable : scoredExecutables) { - try { - return scoredExecutable.execute(); - } catch (Throwable t) { - lastException = t; - } - } - if (lastException != null) { - throw lastException; - } - } - return null; - } - - /** - * Add method. - * - * @param method the method - * @param startIndex the start index - * @param map the map - * @since 0.9.6 - */ - protected void addMethod(Method method, int startIndex, Map> map) { - if (method.isAnnotationPresent(V8Function.class)) { - String methodName = method.getName(); - String aliasMethodName = method.getAnnotation(V8Function.class).name(); - if (aliasMethodName.length() > 0) { - methodName = aliasMethodName; - } - List methods = map.computeIfAbsent(methodName, k -> new ArrayList<>()); - methods.add(method); - } else { - String methodName = method.getName(); - String aliasMethodName = methodName.substring(startIndex); - Matcher matcher = PATTERN_CAPITALIZED_PREFIX.matcher(aliasMethodName); - if (matcher.find()) { - final int capitalizedPrefixLength = matcher.group().length(); - if (capitalizedPrefixLength == 1) { - aliasMethodName = methodName.substring( - startIndex, startIndex + capitalizedPrefixLength).toLowerCase(Locale.ROOT) - + methodName.substring(startIndex + capitalizedPrefixLength); - List methods = map.computeIfAbsent(aliasMethodName, k -> new ArrayList<>()); - methods.add(method); - } else { - for (int i = 1; i < capitalizedPrefixLength; ++i) { - aliasMethodName = methodName.substring(startIndex, startIndex + i).toLowerCase(Locale.ROOT) - + methodName.substring(startIndex + i); - List methods = map.computeIfAbsent(aliasMethodName, k -> new ArrayList<>()); - methods.add(method); - } - } - } else { - List methods = map.computeIfAbsent(aliasMethodName, k -> new ArrayList<>()); - methods.add(method); - } - } - } - - /** - * Gets class descriptor cache. - * - * @return the thread safe map - * @since 1.1.7 - */ - public abstract ThreadSafeMap, ClassDescriptor> getClassDescriptorCache(); - - /** - * Gets from field. - * - * @param property the property - * @return the V8 value - * @throws JavetException the javet exception - * @since 1.1.7 - */ - protected V8Value getFromField(V8Value property) throws JavetException { - if (!classDescriptor.getFieldMap().isEmpty() && property instanceof V8ValueString) { - String propertyName = ((V8ValueString) property).toPrimitive(); - Field field = classDescriptor.getFieldMap().get(propertyName); - if (field != null) { - try { - Object callee = Modifier.isStatic(field.getModifiers()) ? null : targetObject; - Object value = field.get(callee); - if (value != null) { - return v8Runtime.toV8Value(value); - } - } catch (JavetException e) { - throw e; - } catch (Throwable t) { - throw new JavetException(JavetError.CallbackUnknownFailure, - SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); - } - } - } - return null; - } - - /** - * Gets from getter. - * - * @param property the property - * @return the V8 value - * @throws JavetException the javet exception - * @since 1.1.7 - */ - protected V8Value getFromGetter(V8Value property) throws JavetException { - if (!classDescriptor.getGenericGetters().isEmpty()) { - try { - Object propertyObject = v8Runtime.toObject(property); - if (propertyObject != null && !(propertyObject instanceof V8Value)) { - for (Method method : classDescriptor.getGenericGetters()) { - Class[] parameterTypes = method.getParameterTypes(); - Class parameterType = parameterTypes[0]; - Object key = null; - if (V8Value.class.isAssignableFrom(parameterType) - && parameterType.isAssignableFrom(property.getClass())) { - key = property; - } - if (key == null && parameterType.isAssignableFrom(propertyObject.getClass())) { - key = propertyObject; - } - if (key == null && parameterType.isPrimitive()) { - key = JavetTypeUtils.toExactPrimitive(parameterType, propertyObject); - } - if (key == null) { - key = JavetTypeUtils.toApproximatePrimitive(parameterType, propertyObject); - } - if (key != null) { - Object callee = Modifier.isStatic(method.getModifiers()) ? null : targetObject; - Object value = method.invoke(callee, key); - if (value != null) { - return v8Runtime.toV8Value(value); - } - } - } - } - } catch (JavetException e) { - throw e; - } catch (Throwable t) { - throw new JavetException(JavetError.CallbackUnknownFailure, - SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); - } - } - return null; - } - - /** - * Gets from method. - * - * @param target the target - * @param property the property - * @return the V8 value - * @throws JavetException the javet exception - * @since 1.1.7 - */ - protected V8Value getFromMethod(V8Value target, V8Value property) throws JavetException { - if (property instanceof V8ValueString) { - String propertyName = ((V8ValueString) property).toPrimitive(); - List methods = classDescriptor.getMethodsMap().get(propertyName); - if (methods != null && !methods.isEmpty()) { - JavetDynamicProxyInterceptor dynamicProxyInterceptor = new JavetDynamicProxyInterceptor( - dynamicObjectFactory, targetObject, propertyName, methods); - return v8Runtime.createV8ValueFunction(dynamicProxyInterceptor.getCallbackContext()); - } - methods = classDescriptor.getGettersMap().get(propertyName); - if (methods != null && !methods.isEmpty()) { - JavetDynamicProxyInterceptor dynamicProxyInterceptor = new JavetDynamicProxyInterceptor( - dynamicObjectFactory, targetObject, propertyName, methods); - return v8Runtime.toV8Value(dynamicProxyInterceptor.invoke((V8ValueObject) target)); - } - if (FUNCTION_NAME_TO_V8_VALUE.equals(propertyName)) { - return new JavetProxySymbolToPrimitiveConverter<>(v8Runtime, targetObject).getV8ValueFunction(); - } - } - return null; - } - - /** - * Gets getter prefix length. - * - * @param method the method - * @return the getter prefix length - * @since 0.9.6 - */ - protected int getGetterPrefixLength(Method method) { - String methodName = method.getName(); - for (String prefix : GETTER_PREFIX_ARRAY) { - if (methodName.startsWith(prefix) && methodName.length() > prefix.length() - && method.getParameterCount() == 0) { - return prefix.length(); - } - } - return 0; - } - - /** - * Gets setter prefix length. - * - * @param method the method - * @return the setter prefix length - * @since 0.9.6 - */ - protected int getSetterPrefixLength(Method method) { - String methodName = method.getName(); - for (String prefix : SETTER_PREFIX_ARRAY) { - if (methodName.startsWith(prefix) && methodName.length() > prefix.length() - && method.getParameterCount() == 1) { - return prefix.length(); - } - } - return 0; - } - - @Override - public T getTargetObject() { - return targetObject; - } - - /** - * Gets V8 runtime. - * - * @return the V8 runtime - * @since 0.9.6 - */ - public V8Runtime getV8Runtime() { - return v8Runtime; - } - - /** - * Has from generic. - * - * @param property the property - * @return the boolean - * @throws JavetException the javet exception - * @since 1.1.7 - */ - protected boolean hasFromGeneric(V8Value property) throws JavetException { - if (!classDescriptor.getGenericGetters().isEmpty()) { - try { - Object propertyObject = v8Runtime.toObject(property); - if (propertyObject != null && !(propertyObject instanceof V8Value)) { - for (Method method : classDescriptor.getGenericGetters()) { - Class[] parameterTypes = method.getParameterTypes(); - Class parameterType = parameterTypes[0]; - Object key = null; - if (V8Value.class.isAssignableFrom(parameterType) - && parameterType.isAssignableFrom(property.getClass())) { - key = property; - } - if (key == null && parameterType.isAssignableFrom(propertyObject.getClass())) { - key = propertyObject; - } - if (key == null && parameterType.isPrimitive()) { - key = JavetTypeUtils.toExactPrimitive(parameterType, propertyObject); - } - if (key == null) { - key = JavetTypeUtils.toApproximatePrimitive(parameterType, propertyObject); - } - if (key != null) { - Object callee = Modifier.isStatic(method.getModifiers()) ? null : targetObject; - try { - return method.invoke(callee, key) != null; - } catch (Throwable ignored) { - } - } - } - } - } catch (JavetException e) { - throw e; - } catch (Throwable ignored) { - } - } - return false; - } - - /** - * Has from regular. - * - * @param property the property - * @return true : has, false: not has - * @since 1.1.7 - */ - protected boolean hasFromRegular(V8Value property) { - if (property instanceof V8ValueString) { - String propertyName = ((V8ValueString) property).toPrimitive(); - return classDescriptor.getFieldMap().containsKey(propertyName) - || classDescriptor.getMethodsMap().containsKey(propertyName) - || classDescriptor.getGettersMap().containsKey(propertyName) - || classDescriptor.getSettersMap().containsKey(propertyName); - } - return false; - } - - /** - * Initialize. - * - * @since 1.1.7 - */ - protected abstract void initialize(); - - /** - * Initialize constructors. - * - * @param currentClass the current class - * @param conversionMode the conversion mode - * @since 1.1.7 - */ - protected void initializeConstructors(Class currentClass, V8ConversionMode conversionMode) { - for (Constructor constructor : currentClass.getConstructors()) { - if (isAllowed(conversionMode, constructor)) { - classDescriptor.getConstructors().add(constructor); - } - } - } - - /** - * Initialize public fields. - * - * @param currentClass the current class - * @param conversionMode the conversion mode - * @param staticMode the static mode - * @since 1.1.7 - */ - protected void initializePublicFields( - Class currentClass, V8ConversionMode conversionMode, boolean staticMode) { - for (Field field : currentClass.getFields()) { - final int fieldModifiers = field.getModifiers(); - if (staticMode && !Modifier.isStatic(fieldModifiers)) { - continue; - } - if (!(Modifier.isPublic(fieldModifiers))) { - continue; - } - if (!isAllowed(conversionMode, field)) { - continue; - } - String fieldName = field.getName(); - if (field.isAnnotationPresent(V8Property.class)) { - String aliasFieldName = field.getAnnotation(V8Property.class).name(); - if (aliasFieldName.length() > 0) { - fieldName = aliasFieldName; - } - } - if (classDescriptor.getFieldMap().containsKey(fieldName)) { - continue; - } - JavetReflectionUtils.safeSetAccessible(field); - classDescriptor.getFieldMap().put(fieldName, field); - if (!classDescriptor.isTargetTypeMap() && !classDescriptor.isTargetTypeSet()) { - classDescriptor.getUniqueKeySet().add(fieldName); - } - } - } - - /** - * Initialize public methods. - * - * @param currentClass the current class - * @param conversionMode the conversion mode - * @param staticMode the static mode - * @since 1.1.7 - */ - protected void initializePublicMethods( - Class currentClass, V8ConversionMode conversionMode, boolean staticMode) { - for (Method method : currentClass.getMethods()) { - final int methodModifiers = method.getModifiers(); - if (staticMode && !Modifier.isStatic(methodModifiers)) { - continue; - } - if (!(Modifier.isPublic(methodModifiers))) { - continue; - } - if (!isAllowed(conversionMode, method)) { - continue; - } - JavetReflectionUtils.safeSetAccessible(method); - if (isGenericGetter(method)) { - classDescriptor.getGenericGetters().add(method); - } else if (isGenericSetter(method)) { - classDescriptor.getGenericSetters().add(method); - } else if (isApplyFunction(method)) { - classDescriptor.getApplyFunctions().add(method); - } else { - final int getterPrefixLength = getGetterPrefixLength(method); - if (getterPrefixLength > 0) { - addMethod(method, getterPrefixLength, classDescriptor.getGettersMap()); - if (!classDescriptor.isTargetTypeMap() && !classDescriptor.isTargetTypeSet()) { - String aliasMethodName = method.getName().substring(getterPrefixLength); - Matcher matcher = PATTERN_CAPITALIZED_PREFIX.matcher(aliasMethodName); - if (matcher.find()) { - final int capitalizedPrefixLength = matcher.group().length(); - if (capitalizedPrefixLength == 1) { - classDescriptor.getUniqueKeySet().add( - aliasMethodName.substring(0, capitalizedPrefixLength).toLowerCase(Locale.ROOT) - + aliasMethodName.substring(capitalizedPrefixLength)); - } else { - classDescriptor.getUniqueKeySet().add( - aliasMethodName.substring(0, capitalizedPrefixLength - 1).toLowerCase(Locale.ROOT) - + aliasMethodName.substring(capitalizedPrefixLength - 1)); - } - } - } - } else { - final int setterPrefixLength = getSetterPrefixLength(method); - if (setterPrefixLength > 0) { - addMethod(method, setterPrefixLength, classDescriptor.getSettersMap()); - } - } - } - addMethod(method, 0, classDescriptor.getMethodsMap()); - } - } - - /** - * Is allowed. - * - * @param conversionMode the conversion mode - * @param accessibleObject the accessible object - * @return true : allowed, false : disallowed - * @since 1.1.7 - */ - protected boolean isAllowed(V8ConversionMode conversionMode, AccessibleObject accessibleObject) { - switch (conversionMode) { - case AllowOnly: - return accessibleObject.isAnnotationPresent(V8Allow.class); - case BlockOnly: - return !accessibleObject.isAnnotationPresent(V8Block.class); - default: - return true; - } - } - - /** - * Is apply function. - * - * @param method the method - * @return true : yes, false: no - * @since 1.1.7 - */ - protected boolean isApplyFunction(Method method) { - return method.isAnnotationPresent(V8ProxyFunctionApply.class); - } - - /** - * Is generic getter. - * - * @param method the method - * @return true : yes, false : no - * @since 0.9.6 - */ - protected boolean isGenericGetter(Method method) { - if (method.isAnnotationPresent(V8Getter.class)) { - return true; - } - String methodName = method.getName(); - for (String prefix : GETTER_PREFIX_ARRAY) { - if (methodName.equals(prefix) && method.getParameterCount() == 1 && !method.isVarArgs()) { - return true; - } - } - return false; - } - - /** - * Is generic setter. - * - * @param method the method - * @return true : yes, false : no - * @since 0.9.6 - */ - protected boolean isGenericSetter(Method method) { - if (method.isAnnotationPresent(V8Setter.class)) { - return true; - } - String methodName = method.getName(); - for (String prefix : SETTER_PREFIX_ARRAY) { - if (methodName.equals(prefix) && method.getParameterCount() == 2 && !method.isVarArgs()) { - return true; - } - } - return false; - } - - /** - * Sets to field. - * - * @param propertyKey the property key - * @param propertyValue the property value - * @return true : set, false: not set - * @throws JavetException the javet exception - * @since 1.1.7 - */ - protected boolean setToField(V8Value propertyKey, V8Value propertyValue) throws JavetException { - if (!classDescriptor.getFieldMap().isEmpty() && propertyKey instanceof V8ValueString) { - String propertyName = ((V8ValueString) propertyKey).toPrimitive(); - Field field = classDescriptor.getFieldMap().get(propertyName); - if (field != null) { - final int fieldModifiers = field.getModifiers(); - if (!Modifier.isFinal(fieldModifiers)) { - try { - Object callee = Modifier.isStatic(fieldModifiers) ? null : targetObject; - field.set(callee, v8Runtime.toObject(propertyValue)); - return true; - } catch (JavetException e) { - throw e; - } catch (Throwable t) { - throw new JavetException(JavetError.CallbackUnknownFailure, - SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); - } - } - } - } - return false; - } - - /** - * Sets to setter. - * - * @param target the target - * @param propertyKey the property key - * @param propertyValue the property value - * @return true : set, false: not set - * @throws JavetException the javet exception - * @since 1.1.7 - */ - protected boolean setToSetter(V8Value target, V8Value propertyKey, V8Value propertyValue) throws JavetException { - if (!classDescriptor.getGenericSetters().isEmpty() || !classDescriptor.getSettersMap().isEmpty()) { - Object keyObject, valueObject; - try { - keyObject = v8Runtime.toObject(propertyKey); - valueObject = v8Runtime.toObject(propertyValue); - } catch (JavetException e) { - throw e; - } catch (Throwable t) { - throw new JavetException(JavetError.CallbackUnknownFailure, - SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); - } - if (!classDescriptor.getGenericSetters().isEmpty() && keyObject != null && !(keyObject instanceof V8Value)) { - try { - for (Method method : classDescriptor.getGenericSetters()) { - Class[] parameterTypes = method.getParameterTypes(); - Class keyParameterType = parameterTypes[0]; - Class valueParameterType = parameterTypes[1]; - Object key = null; - Object value = null; - if (V8Value.class.isAssignableFrom(keyParameterType) - && keyParameterType.isAssignableFrom(propertyKey.getClass())) { - key = propertyKey; - } - if (V8Value.class.isAssignableFrom(valueParameterType) - && valueParameterType.isAssignableFrom(propertyValue.getClass())) { - value = propertyValue; - } - if (key == null && keyParameterType.isAssignableFrom(keyObject.getClass())) { - key = keyObject; - } - if (value == null && valueParameterType.isAssignableFrom(valueObject.getClass())) { - value = valueObject; - } - if (key == null && keyParameterType.isPrimitive()) { - key = JavetTypeUtils.toExactPrimitive(keyParameterType, keyObject); - } - if (value == null && valueParameterType.isPrimitive()) { - value = JavetTypeUtils.toExactPrimitive(valueParameterType, valueObject); - } - if (key == null) { - key = JavetTypeUtils.toApproximatePrimitive(keyParameterType, keyObject); - } - if (value == null) { - value = JavetTypeUtils.toApproximatePrimitive(valueParameterType, valueObject); - } - if (key != null) { - Object callee = Modifier.isStatic(method.getModifiers()) ? null : targetObject; - method.invoke(callee, key, value); - return true; - } - } - } catch (Throwable t) { - throw new JavetException(JavetError.CallbackUnknownFailure, - SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); - } - } - if (keyObject instanceof String) { - String propertyName = (String) keyObject; - List methods = classDescriptor.getSettersMap().get(propertyName); - if (methods != null) { - JavetDynamicProxyInterceptor dynamicProxyInterceptor = new JavetDynamicProxyInterceptor( - dynamicObjectFactory, targetObject, propertyName, methods); - dynamicProxyInterceptor.invoke((V8ValueObject) target, propertyValue); - return true; - } - } - } - return false; - } -} +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interop.proxy; + +import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.callback.IJavetDirectCallable; +import com.caoccao.javet.interop.callback.JavetCallbackContext; + +import java.util.Objects; + +/** + * The type Base javet proxy handler. + * + * @param the type parameter + * @param the type parameter + * @since 2.2.0 + */ +public abstract class BaseJavetProxyHandler + implements IJavetProxyHandler, IJavetDirectCallable { + /** + * The Callback contexts. + * + * @since 2.2.0 + */ + protected JavetCallbackContext[] callbackContexts; + /** + * The Target object. + * + * @since 0.9.6 + */ + protected T targetObject; + /** + * The V8 runtime. + * + * @since 0.9.6 + */ + protected V8Runtime v8Runtime; + + /** + * Instantiates a new Base javet proxy handler. + * + * @param v8Runtime the V8 runtime + * @param targetObject the target object + * @since 2.2.0 + */ + public BaseJavetProxyHandler(V8Runtime v8Runtime, T targetObject) { + callbackContexts = null; + this.targetObject = Objects.requireNonNull(targetObject); + this.v8Runtime = Objects.requireNonNull(v8Runtime); + } + + @Override + public T getTargetObject() { + return targetObject; + } + + @Override + public V8Runtime getV8Runtime() { + return v8Runtime; + } +} diff --git a/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetProxySymbolConverter.java b/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetProxySymbolConverter.java index 0c59a4f02..1644b1634 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetProxySymbolConverter.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetProxySymbolConverter.java @@ -17,12 +17,12 @@ package com.caoccao.javet.interop.proxy; import com.caoccao.javet.annotations.CheckReturnValue; -import com.caoccao.javet.exceptions.JavetError; import com.caoccao.javet.exceptions.JavetException; import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.callback.IJavetDirectCallable; import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; import com.caoccao.javet.interop.converters.JavetObjectConverter; -import com.caoccao.javet.utils.SimpleMap; import com.caoccao.javet.values.V8Value; import com.caoccao.javet.values.reference.V8ValueFunction; @@ -79,16 +79,12 @@ public BaseJavetProxySymbolConverter(V8Runtime v8Runtime, T targetObject) { @CheckReturnValue @Override public V8ValueFunction getV8ValueFunction() throws JavetException { - try { - JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - this, getClass().getMethod(METHOD_NAME_TO_V8_VALUE, V8Value[].class)); - return v8Runtime.createV8ValueFunction(javetCallbackContext); - } catch (NoSuchMethodException e) { - throw new JavetException(JavetError.CallbackMethodFailure, - SimpleMap.of( - JavetError.PARAMETER_METHOD_NAME, METHOD_NAME_TO_V8_VALUE, - JavetError.PARAMETER_MESSAGE, e.getMessage()), e); - } + JavetCallbackContext javetCallbackContext = new JavetCallbackContext( + METHOD_NAME_TO_V8_VALUE, + this, + JavetCallbackType.DirectCallNoThisAndResult, + (IJavetDirectCallable.NoThisAndResult) this::toV8Value); + return v8Runtime.createV8ValueFunction(javetCallbackContext); } /** @@ -100,6 +96,7 @@ public V8ValueFunction getV8ValueFunction() throws JavetException { * @since 1.0.4 */ @CheckReturnValue + @Override public V8Value toV8Value(V8Value... v8Values) throws JavetException { return OBJECT_CONVERTER.toV8Value(v8Runtime, targetObject); } diff --git a/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetReflectionProxyHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetReflectionProxyHandler.java new file mode 100644 index 000000000..dc84597e4 --- /dev/null +++ b/src/main/java/com/caoccao/javet/interop/proxy/BaseJavetReflectionProxyHandler.java @@ -0,0 +1,706 @@ +/* + * Copyright (c) 2021-2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interop.proxy; + +import com.caoccao.javet.annotations.*; +import com.caoccao.javet.enums.V8ConversionMode; +import com.caoccao.javet.exceptions.JavetError; +import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.binding.ClassDescriptor; +import com.caoccao.javet.utils.*; +import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.primitive.V8ValueString; +import com.caoccao.javet.values.reference.V8ValueObject; + +import java.lang.reflect.*; +import java.util.ArrayList; +import java.util.List; +import java.util.Locale; +import java.util.Map; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +/** + * The type Base javet reflection proxy handler. + * + * @param the type parameter + * @param the type parameter + * @since 0.9.6 + */ +public abstract class BaseJavetReflectionProxyHandler + extends BaseJavetProxyHandler { + /** + * The constant GETTER_PREFIX_ARRAY. + * + * @since 0.9.6 + */ + protected static final String[] GETTER_PREFIX_ARRAY = new String[]{"get", "is"}; + /** + * The constant PATTERN_CAPITALIZED_PREFIX. + * + * @since 0.9.7 + */ + protected static final Pattern PATTERN_CAPITALIZED_PREFIX = Pattern.compile("^[A-Z]+"); + /** + * The constant SETTER_PREFIX_ARRAY. + * + * @since 0.9.6 + */ + protected static final String[] SETTER_PREFIX_ARRAY = new String[]{"set", "put"}; + /** + * The Class descriptor. + * + * @since 1.1.7 + */ + protected ClassDescriptor classDescriptor; + /** + * The Reflection object factory. + * + * @since 2.0.1 + */ + protected IJavetReflectionObjectFactory reflectionObjectFactory; + + /** + * Instantiates a new Base javet reflection proxy handler. + * + * @param v8Runtime the V8 runtime + * @param reflectionObjectFactory the reflection object factory + * @param targetObject the target object + * @since 0.9.6 + */ + public BaseJavetReflectionProxyHandler( + V8Runtime v8Runtime, + IJavetReflectionObjectFactory reflectionObjectFactory, + T targetObject) { + super(v8Runtime, targetObject); + this.reflectionObjectFactory = reflectionObjectFactory; + initialize(); + } + + /** + * Execute. + * + * @param the type parameter + * @param reflectionObjectFactory the reflection object factory + * @param targetObject the target object + * @param thisObject this object + * @param executables the executables + * @param javetVirtualObjects the javet virtual objects + * @return the object + * @throws Throwable the throwable + * @since 0.9.10 + */ + protected static Object execute( + IJavetReflectionObjectFactory reflectionObjectFactory, + Object targetObject, + V8ValueObject thisObject, + List executables, + JavetVirtualObject[] javetVirtualObjects) throws Throwable { + List> scoredExecutables = new ArrayList<>(); + for (E executable : executables) { + ScoredExecutable scoredExecutable = new ScoredExecutable<>( + reflectionObjectFactory, targetObject, thisObject, executable, javetVirtualObjects); + scoredExecutable.calculateScore(); + double score = scoredExecutable.getScore(); + if (score > 0) { + scoredExecutables.add(scoredExecutable); + } + } + if (!scoredExecutables.isEmpty()) { + scoredExecutables.sort((o1, o2) -> Double.compare(o2.getScore(), o1.getScore())); + Throwable lastException = null; + for (ScoredExecutable scoredExecutable : scoredExecutables) { + try { + return scoredExecutable.execute(); + } catch (Throwable t) { + lastException = t; + } + } + if (lastException != null) { + throw lastException; + } + } + return null; + } + + /** + * Add method. + * + * @param method the method + * @param startIndex the start index + * @param map the map + * @since 0.9.6 + */ + protected void addMethod(Method method, int startIndex, Map> map) { + if (method.isAnnotationPresent(V8Function.class)) { + String methodName = method.getName(); + String aliasMethodName = method.getAnnotation(V8Function.class).name(); + if (aliasMethodName.length() > 0) { + methodName = aliasMethodName; + } + List methods = map.computeIfAbsent(methodName, k -> new ArrayList<>()); + methods.add(method); + } else { + String methodName = method.getName(); + String aliasMethodName = methodName.substring(startIndex); + Matcher matcher = PATTERN_CAPITALIZED_PREFIX.matcher(aliasMethodName); + if (matcher.find()) { + final int capitalizedPrefixLength = matcher.group().length(); + if (capitalizedPrefixLength == 1) { + aliasMethodName = methodName.substring( + startIndex, startIndex + capitalizedPrefixLength).toLowerCase(Locale.ROOT) + + methodName.substring(startIndex + capitalizedPrefixLength); + List methods = map.computeIfAbsent(aliasMethodName, k -> new ArrayList<>()); + methods.add(method); + } else { + for (int i = 1; i < capitalizedPrefixLength; ++i) { + aliasMethodName = methodName.substring(startIndex, startIndex + i).toLowerCase(Locale.ROOT) + + methodName.substring(startIndex + i); + List methods = map.computeIfAbsent(aliasMethodName, k -> new ArrayList<>()); + methods.add(method); + } + } + } else { + List methods = map.computeIfAbsent(aliasMethodName, k -> new ArrayList<>()); + methods.add(method); + } + } + } + + /** + * Gets class descriptor cache. + * + * @return the thread safe map + * @since 1.1.7 + */ + public abstract ThreadSafeMap, ClassDescriptor> getClassDescriptorCache(); + + /** + * Gets from field. + * + * @param property the property + * @return the V8 value + * @throws JavetException the javet exception + * @since 1.1.7 + */ + protected V8Value getFromField(V8Value property) throws JavetException { + if (!classDescriptor.getFieldMap().isEmpty() && property instanceof V8ValueString) { + String propertyName = ((V8ValueString) property).toPrimitive(); + Field field = classDescriptor.getFieldMap().get(propertyName); + if (field != null) { + try { + Object callee = Modifier.isStatic(field.getModifiers()) ? null : targetObject; + Object value = field.get(callee); + if (value != null) { + return v8Runtime.toV8Value(value); + } + } catch (JavetException e) { + throw e; + } catch (Throwable t) { + throw new JavetException(JavetError.CallbackUnknownFailure, + SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); + } + } + } + return null; + } + + /** + * Gets from getter. + * + * @param property the property + * @return the V8 value + * @throws JavetException the javet exception + * @since 1.1.7 + */ + protected V8Value getFromGetter(V8Value property) throws JavetException { + if (!classDescriptor.getGenericGetters().isEmpty()) { + try { + Object propertyObject = v8Runtime.toObject(property); + if (propertyObject != null && !(propertyObject instanceof V8Value)) { + for (Method method : classDescriptor.getGenericGetters()) { + Class[] parameterTypes = method.getParameterTypes(); + Class parameterType = parameterTypes[0]; + Object key = null; + if (V8Value.class.isAssignableFrom(parameterType) + && parameterType.isAssignableFrom(property.getClass())) { + key = property; + } + if (key == null && parameterType.isAssignableFrom(propertyObject.getClass())) { + key = propertyObject; + } + if (key == null && parameterType.isPrimitive()) { + key = JavetTypeUtils.toExactPrimitive(parameterType, propertyObject); + } + if (key == null) { + key = JavetTypeUtils.toApproximatePrimitive(parameterType, propertyObject); + } + if (key != null) { + Object callee = Modifier.isStatic(method.getModifiers()) ? null : targetObject; + Object value = method.invoke(callee, key); + if (value != null) { + return v8Runtime.toV8Value(value); + } + } + } + } + } catch (JavetException e) { + throw e; + } catch (Throwable t) { + throw new JavetException(JavetError.CallbackUnknownFailure, + SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); + } + } + return null; + } + + /** + * Gets from method. + * + * @param target the target + * @param property the property + * @return the V8 value + * @throws JavetException the javet exception + * @since 1.1.7 + */ + protected V8Value getFromMethod(V8Value target, V8Value property) throws JavetException { + if (property instanceof V8ValueString) { + String propertyName = ((V8ValueString) property).toPrimitive(); + List methods = classDescriptor.getMethodsMap().get(propertyName); + if (methods != null && !methods.isEmpty()) { + JavetReflectionProxyInterceptor reflectionProxyInterceptor = new JavetReflectionProxyInterceptor( + reflectionObjectFactory, targetObject, propertyName, methods); + return v8Runtime.createV8ValueFunction(reflectionProxyInterceptor.getCallbackContext()); + } + methods = classDescriptor.getGettersMap().get(propertyName); + if (methods != null && !methods.isEmpty()) { + JavetReflectionProxyInterceptor reflectionProxyInterceptor = new JavetReflectionProxyInterceptor( + reflectionObjectFactory, targetObject, propertyName, methods); + return v8Runtime.toV8Value(reflectionProxyInterceptor.invoke((V8ValueObject) target)); + } + if (FUNCTION_NAME_TO_V8_VALUE.equals(propertyName)) { + return new JavetProxySymbolToPrimitiveConverter<>(v8Runtime, targetObject).getV8ValueFunction(); + } + } + return null; + } + + /** + * Gets getter prefix length. + * + * @param method the method + * @return the getter prefix length + * @since 0.9.6 + */ + protected int getGetterPrefixLength(Method method) { + String methodName = method.getName(); + for (String prefix : GETTER_PREFIX_ARRAY) { + if (methodName.startsWith(prefix) && methodName.length() > prefix.length() + && method.getParameterCount() == 0) { + return prefix.length(); + } + } + return 0; + } + + /** + * Gets setter prefix length. + * + * @param method the method + * @return the setter prefix length + * @since 0.9.6 + */ + protected int getSetterPrefixLength(Method method) { + String methodName = method.getName(); + for (String prefix : SETTER_PREFIX_ARRAY) { + if (methodName.startsWith(prefix) && methodName.length() > prefix.length() + && method.getParameterCount() == 1) { + return prefix.length(); + } + } + return 0; + } + + /** + * Has from generic. + * + * @param property the property + * @return the boolean + * @throws JavetException the javet exception + * @since 1.1.7 + */ + protected boolean hasFromGeneric(V8Value property) throws JavetException { + if (!classDescriptor.getGenericGetters().isEmpty()) { + try { + Object propertyObject = v8Runtime.toObject(property); + if (propertyObject != null && !(propertyObject instanceof V8Value)) { + for (Method method : classDescriptor.getGenericGetters()) { + Class[] parameterTypes = method.getParameterTypes(); + Class parameterType = parameterTypes[0]; + Object key = null; + if (V8Value.class.isAssignableFrom(parameterType) + && parameterType.isAssignableFrom(property.getClass())) { + key = property; + } + if (key == null && parameterType.isAssignableFrom(propertyObject.getClass())) { + key = propertyObject; + } + if (key == null && parameterType.isPrimitive()) { + key = JavetTypeUtils.toExactPrimitive(parameterType, propertyObject); + } + if (key == null) { + key = JavetTypeUtils.toApproximatePrimitive(parameterType, propertyObject); + } + if (key != null) { + Object callee = Modifier.isStatic(method.getModifiers()) ? null : targetObject; + try { + return method.invoke(callee, key) != null; + } catch (Throwable ignored) { + } + } + } + } + } catch (JavetException e) { + throw e; + } catch (Throwable ignored) { + } + } + return false; + } + + /** + * Has from regular. + * + * @param property the property + * @return true : has, false: not has + * @since 1.1.7 + */ + protected boolean hasFromRegular(V8Value property) { + if (property instanceof V8ValueString) { + String propertyName = ((V8ValueString) property).toPrimitive(); + return classDescriptor.getFieldMap().containsKey(propertyName) + || classDescriptor.getMethodsMap().containsKey(propertyName) + || classDescriptor.getGettersMap().containsKey(propertyName) + || classDescriptor.getSettersMap().containsKey(propertyName); + } + return false; + } + + /** + * Initialize. + * + * @since 1.1.7 + */ + protected abstract void initialize(); + + /** + * Initialize constructors. + * + * @param currentClass the current class + * @param conversionMode the conversion mode + * @since 1.1.7 + */ + protected void initializeConstructors(Class currentClass, V8ConversionMode conversionMode) { + for (Constructor constructor : currentClass.getConstructors()) { + if (isAllowed(conversionMode, constructor)) { + classDescriptor.getConstructors().add(constructor); + } + } + } + + /** + * Initialize public fields. + * + * @param currentClass the current class + * @param conversionMode the conversion mode + * @param staticMode the static mode + * @since 1.1.7 + */ + protected void initializePublicFields( + Class currentClass, V8ConversionMode conversionMode, boolean staticMode) { + for (Field field : currentClass.getFields()) { + final int fieldModifiers = field.getModifiers(); + if (staticMode && !Modifier.isStatic(fieldModifiers)) { + continue; + } + if (!(Modifier.isPublic(fieldModifiers))) { + continue; + } + if (!isAllowed(conversionMode, field)) { + continue; + } + String fieldName = field.getName(); + if (field.isAnnotationPresent(V8Property.class)) { + String aliasFieldName = field.getAnnotation(V8Property.class).name(); + if (aliasFieldName.length() > 0) { + fieldName = aliasFieldName; + } + } + if (classDescriptor.getFieldMap().containsKey(fieldName)) { + continue; + } + JavetReflectionUtils.safeSetAccessible(field); + classDescriptor.getFieldMap().put(fieldName, field); + if (!classDescriptor.isTargetTypeMap() && !classDescriptor.isTargetTypeSet()) { + classDescriptor.getUniqueKeySet().add(fieldName); + } + } + } + + /** + * Initialize public methods. + * + * @param currentClass the current class + * @param conversionMode the conversion mode + * @param staticMode the static mode + * @since 1.1.7 + */ + protected void initializePublicMethods( + Class currentClass, V8ConversionMode conversionMode, boolean staticMode) { + for (Method method : currentClass.getMethods()) { + final int methodModifiers = method.getModifiers(); + if (staticMode && !Modifier.isStatic(methodModifiers)) { + continue; + } + if (!(Modifier.isPublic(methodModifiers))) { + continue; + } + if (!isAllowed(conversionMode, method)) { + continue; + } + JavetReflectionUtils.safeSetAccessible(method); + if (isGenericGetter(method)) { + classDescriptor.getGenericGetters().add(method); + } else if (isGenericSetter(method)) { + classDescriptor.getGenericSetters().add(method); + } else if (isApplyFunction(method)) { + classDescriptor.getApplyFunctions().add(method); + } else { + final int getterPrefixLength = getGetterPrefixLength(method); + if (getterPrefixLength > 0) { + addMethod(method, getterPrefixLength, classDescriptor.getGettersMap()); + if (!classDescriptor.isTargetTypeMap() && !classDescriptor.isTargetTypeSet()) { + String aliasMethodName = method.getName().substring(getterPrefixLength); + Matcher matcher = PATTERN_CAPITALIZED_PREFIX.matcher(aliasMethodName); + if (matcher.find()) { + final int capitalizedPrefixLength = matcher.group().length(); + if (capitalizedPrefixLength == 1) { + classDescriptor.getUniqueKeySet().add( + aliasMethodName.substring(0, capitalizedPrefixLength).toLowerCase(Locale.ROOT) + + aliasMethodName.substring(capitalizedPrefixLength)); + } else { + classDescriptor.getUniqueKeySet().add( + aliasMethodName.substring(0, capitalizedPrefixLength - 1).toLowerCase(Locale.ROOT) + + aliasMethodName.substring(capitalizedPrefixLength - 1)); + } + } + } + } else { + final int setterPrefixLength = getSetterPrefixLength(method); + if (setterPrefixLength > 0) { + addMethod(method, setterPrefixLength, classDescriptor.getSettersMap()); + } + } + } + addMethod(method, 0, classDescriptor.getMethodsMap()); + } + } + + /** + * Is allowed. + * + * @param conversionMode the conversion mode + * @param accessibleObject the accessible object + * @return true : allowed, false : disallowed + * @since 1.1.7 + */ + protected boolean isAllowed(V8ConversionMode conversionMode, AccessibleObject accessibleObject) { + switch (conversionMode) { + case AllowOnly: + return accessibleObject.isAnnotationPresent(V8Allow.class); + case BlockOnly: + return !accessibleObject.isAnnotationPresent(V8Block.class); + default: + return true; + } + } + + /** + * Is apply function. + * + * @param method the method + * @return true : yes, false: no + * @since 1.1.7 + */ + protected boolean isApplyFunction(Method method) { + return method.isAnnotationPresent(V8ProxyFunctionApply.class); + } + + /** + * Is generic getter. + * + * @param method the method + * @return true : yes, false : no + * @since 0.9.6 + */ + protected boolean isGenericGetter(Method method) { + if (method.isAnnotationPresent(V8Getter.class)) { + return true; + } + String methodName = method.getName(); + for (String prefix : GETTER_PREFIX_ARRAY) { + if (methodName.equals(prefix) && method.getParameterCount() == 1 && !method.isVarArgs()) { + return true; + } + } + return false; + } + + /** + * Is generic setter. + * + * @param method the method + * @return true : yes, false : no + * @since 0.9.6 + */ + protected boolean isGenericSetter(Method method) { + if (method.isAnnotationPresent(V8Setter.class)) { + return true; + } + String methodName = method.getName(); + for (String prefix : SETTER_PREFIX_ARRAY) { + if (methodName.equals(prefix) && method.getParameterCount() == 2 && !method.isVarArgs()) { + return true; + } + } + return false; + } + + /** + * Sets to field. + * + * @param propertyKey the property key + * @param propertyValue the property value + * @return true : set, false: not set + * @throws JavetException the javet exception + * @since 1.1.7 + */ + protected boolean setToField(V8Value propertyKey, V8Value propertyValue) throws JavetException { + if (!classDescriptor.getFieldMap().isEmpty() && propertyKey instanceof V8ValueString) { + String propertyName = ((V8ValueString) propertyKey).toPrimitive(); + Field field = classDescriptor.getFieldMap().get(propertyName); + if (field != null) { + final int fieldModifiers = field.getModifiers(); + if (!Modifier.isFinal(fieldModifiers)) { + try { + Object callee = Modifier.isStatic(fieldModifiers) ? null : targetObject; + field.set(callee, v8Runtime.toObject(propertyValue)); + return true; + } catch (JavetException e) { + throw e; + } catch (Throwable t) { + throw new JavetException(JavetError.CallbackUnknownFailure, + SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); + } + } + } + } + return false; + } + + /** + * Sets to setter. + * + * @param target the target + * @param propertyKey the property key + * @param propertyValue the property value + * @return true : set, false: not set + * @throws JavetException the javet exception + * @since 1.1.7 + */ + protected boolean setToSetter(V8Value target, V8Value propertyKey, V8Value propertyValue) throws JavetException { + if (!classDescriptor.getGenericSetters().isEmpty() || !classDescriptor.getSettersMap().isEmpty()) { + Object keyObject, valueObject; + try { + keyObject = v8Runtime.toObject(propertyKey); + valueObject = v8Runtime.toObject(propertyValue); + } catch (JavetException e) { + throw e; + } catch (Throwable t) { + throw new JavetException(JavetError.CallbackUnknownFailure, + SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); + } + if (!classDescriptor.getGenericSetters().isEmpty() && keyObject != null && !(keyObject instanceof V8Value)) { + try { + for (Method method : classDescriptor.getGenericSetters()) { + Class[] parameterTypes = method.getParameterTypes(); + Class keyParameterType = parameterTypes[0]; + Class valueParameterType = parameterTypes[1]; + Object key = null; + Object value = null; + if (V8Value.class.isAssignableFrom(keyParameterType) + && keyParameterType.isAssignableFrom(propertyKey.getClass())) { + key = propertyKey; + } + if (V8Value.class.isAssignableFrom(valueParameterType) + && valueParameterType.isAssignableFrom(propertyValue.getClass())) { + value = propertyValue; + } + if (key == null && keyParameterType.isAssignableFrom(keyObject.getClass())) { + key = keyObject; + } + if (value == null && valueParameterType.isAssignableFrom(valueObject.getClass())) { + value = valueObject; + } + if (key == null && keyParameterType.isPrimitive()) { + key = JavetTypeUtils.toExactPrimitive(keyParameterType, keyObject); + } + if (value == null && valueParameterType.isPrimitive()) { + value = JavetTypeUtils.toExactPrimitive(valueParameterType, valueObject); + } + if (key == null) { + key = JavetTypeUtils.toApproximatePrimitive(keyParameterType, keyObject); + } + if (value == null) { + value = JavetTypeUtils.toApproximatePrimitive(valueParameterType, valueObject); + } + if (key != null) { + Object callee = Modifier.isStatic(method.getModifiers()) ? null : targetObject; + method.invoke(callee, key, value); + return true; + } + } + } catch (Throwable t) { + throw new JavetException(JavetError.CallbackUnknownFailure, + SimpleMap.of(JavetError.PARAMETER_MESSAGE, t.getMessage()), t); + } + } + if (keyObject instanceof String) { + String propertyName = (String) keyObject; + List methods = classDescriptor.getSettersMap().get(propertyName); + if (methods != null) { + JavetReflectionProxyInterceptor reflectionProxyInterceptor = new JavetReflectionProxyInterceptor( + reflectionObjectFactory, targetObject, propertyName, methods); + reflectionProxyInterceptor.invoke((V8ValueObject) target, propertyValue); + return true; + } + } + } + return false; + } +} diff --git a/src/main/java/com/caoccao/javet/interop/proxy/IJavetDirectProxyHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/IJavetDirectProxyHandler.java new file mode 100644 index 000000000..cc789be82 --- /dev/null +++ b/src/main/java/com/caoccao/javet/interop/proxy/IJavetDirectProxyHandler.java @@ -0,0 +1,295 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interop.proxy; + +import com.caoccao.javet.enums.V8ValueSymbolType; +import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interfaces.IJavetBiFunction; +import com.caoccao.javet.interfaces.IJavetUniFunction; +import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.V8Scope; +import com.caoccao.javet.interop.callback.IJavetDirectCallable; +import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; +import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.primitive.V8ValueBoolean; +import com.caoccao.javet.values.primitive.V8ValueString; +import com.caoccao.javet.values.reference.V8ValueArray; +import com.caoccao.javet.values.reference.V8ValueSymbol; +import com.caoccao.javet.values.reference.builtin.V8ValueBuiltInSymbol; + +import java.util.Map; + +/** + * The interface Javet direct proxy handler. + * + * @param the type parameter + * @since 2.2.0 + */ +public interface IJavetDirectProxyHandler { + /** + * Gets V8 runtime. + * + * @return the V8 runtime + * @since 2.2.0 + */ + V8Runtime getV8Runtime(); + + /** + * Apply to object. + * + * @param target the target + * @param thisObject this object + * @param arguments the arguments + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8Value proxyApply(V8Value target, V8Value thisObject, V8ValueArray arguments) throws JavetException, E { + return getV8Runtime().createV8ValueUndefined(); + } + + /** + * Get by property. + * + * @param target the target + * @param property the property + * @param receiver the receiver + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8Value proxyGet(V8Value target, V8Value property, V8Value receiver) throws JavetException, E { + if (property instanceof V8ValueString) { + String propertyString = ((V8ValueString) property).toPrimitive(); + Map> stringGetterMap = proxyGetStringGetterMap(); + if (stringGetterMap != null && !stringGetterMap.isEmpty()) { + IJavetUniFunction getter = stringGetterMap.get(propertyString); + if (getter != null) { + return getter.apply(propertyString); + } + } + if (IJavetProxyHandler.FUNCTION_NAME_TO_V8_VALUE.equals(propertyString)) { + return getV8Runtime().createV8ValueFunction( + new JavetCallbackContext( + V8ValueBuiltInSymbol.SYMBOL_PROPERTY_TO_PRIMITIVE, + V8ValueSymbolType.BuiltIn, + JavetCallbackType.DirectCallNoThisAndResult, + (IJavetDirectCallable.NoThisAndResult) this::symbolToPrimitive)); + } + } else if (property instanceof V8ValueSymbol) { + V8ValueSymbol propertySymbol = (V8ValueSymbol) property; + String description = propertySymbol.getDescription(); + Map> symbolGetterMap = proxyGetSymbolGetterMap(); + if (symbolGetterMap != null && !symbolGetterMap.isEmpty()) { + IJavetUniFunction getter = symbolGetterMap.get(description); + if (getter != null) { + return getter.apply(propertySymbol); + } + } + if (V8ValueBuiltInSymbol.SYMBOL_PROPERTY_TO_PRIMITIVE.equals(description)) { + return getV8Runtime().createV8ValueFunction( + new JavetCallbackContext( + V8ValueBuiltInSymbol.SYMBOL_PROPERTY_TO_PRIMITIVE, + V8ValueSymbolType.BuiltIn, + JavetCallbackType.DirectCallNoThisAndResult, + (IJavetDirectCallable.NoThisAndResult) this::symbolToPrimitive)); + } else if (V8ValueBuiltInSymbol.SYMBOL_PROPERTY_ITERATOR.equals(description)) { + return getV8Runtime().createV8ValueFunction( + new JavetCallbackContext( + V8ValueBuiltInSymbol.SYMBOL_PROPERTY_ITERATOR, + V8ValueSymbolType.BuiltIn, + JavetCallbackType.DirectCallNoThisAndResult, + (IJavetDirectCallable.NoThisAndResult) this::symbolIterator)); + } + } + return getV8Runtime().createV8ValueUndefined(); + } + + /** + * Proxy get string getter map. + * + * @return the map + * @since 2.2.0 + */ + default Map> proxyGetStringGetterMap() { + return null; + } + + /** + * Proxy get string setter map. + * + * @return the map + * @since 2.2.0 + */ + default Map> proxyGetStringSetterMap() { + return null; + } + + /** + * Proxy get symbol getter map. + * + * @return the map + * @since 2.2.0 + */ + default Map> proxyGetSymbolGetterMap() { + return null; + } + + /** + * Proxy get symbol setter map. + * + * @return the map + * @since 2.2.0 + */ + default Map> proxyGetSymbolSetterMap() { + return null; + } + + /** + * Has property + * + * @param target the target + * @param property the property + * @return the V8 value boolean + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8ValueBoolean proxyHas(V8Value target, V8Value property) throws JavetException, E { + boolean hasProperty = false; + if (property instanceof V8ValueString) { + String propertyString = ((V8ValueString) property).toPrimitive(); + Map> stringGetterMap = proxyGetStringGetterMap(); + if (stringGetterMap != null && !stringGetterMap.isEmpty()) { + hasProperty = stringGetterMap.containsKey(propertyString); + } + } + if (!hasProperty && property instanceof V8ValueSymbol) { + V8ValueSymbol propertySymbol = (V8ValueSymbol) property; + String description = propertySymbol.getDescription(); + Map> symbolGetterMap = proxyGetSymbolGetterMap(); + if (symbolGetterMap != null && !symbolGetterMap.isEmpty()) { + hasProperty = symbolGetterMap.containsKey(description); + } + } + return getV8Runtime().createV8ValueBoolean(hasProperty); + } + + /** + * Own keys. + * + * @param target the target + * @return the V8 value array + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8ValueArray proxyOwnKeys(V8Value target) throws JavetException, E { + try (V8Scope v8Scope = getV8Runtime().getV8Scope()) { + V8ValueArray v8ValueArray = v8Scope.createV8ValueArray(); + Map> stringGetterMap = proxyGetStringGetterMap(); + if (stringGetterMap != null && !stringGetterMap.isEmpty()) { + V8ValueString[] v8ValueStrings = new V8ValueString[stringGetterMap.size()]; + int index = 0; + for (String key : stringGetterMap.keySet()) { + v8ValueStrings[index++] = getV8Runtime().createV8ValueString(key); + } + v8ValueArray.push((Object[]) v8ValueStrings); + } + v8Scope.setEscapable(); + return v8ValueArray; + } + } + + /** + * Set value by property. + * + * @param target the target + * @param propertyKey the property key + * @param propertyValue the property value + * @param receiver the receiver + * @return the V8 value boolean + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8ValueBoolean proxySet( + V8Value target, V8Value propertyKey, V8Value propertyValue, V8Value receiver) + throws JavetException, E { + boolean isSet = false; + if (propertyKey instanceof V8ValueString) { + String propertyKeyString = ((V8ValueString) propertyKey).toPrimitive(); + Map> stringSetterMap = proxyGetStringSetterMap(); + if (stringSetterMap != null && !stringSetterMap.isEmpty()) { + IJavetBiFunction setter = stringSetterMap.get(propertyKeyString); + if (setter != null) { + isSet = setter.apply(propertyKeyString, propertyValue); + } + } + } + if (!isSet && propertyKey instanceof V8ValueSymbol) { + V8ValueSymbol propertyKeySymbol = (V8ValueSymbol) propertyKey; + String description = propertyKeySymbol.getDescription(); + Map> symbolSetterMap = proxyGetSymbolSetterMap(); + if (symbolSetterMap != null && !symbolSetterMap.isEmpty()) { + IJavetBiFunction setter = symbolSetterMap.get(description); + if (setter != null) { + isSet = setter.apply(propertyKeySymbol, propertyValue); + } + } + } + return getV8Runtime().createV8ValueBoolean(isSet); + } + + /** + * Sets V8 runtime. + * + * @param v8Runtime the V8 runtime + * @since 2.2.0 + */ + default void setV8Runtime(V8Runtime v8Runtime) { + } + + /** + * Symbol iterator. + * + * @param v8Values the V8 values + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8Value symbolIterator(V8Value... v8Values) throws JavetException, E { + return getV8Runtime().createV8ValueUndefined(); + } + + /** + * Symbol toPrimitive. + * + * @param v8Values the V8 values + * @return the V8 value + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8Value symbolToPrimitive(V8Value... v8Values) throws JavetException, E { + return getV8Runtime().createV8ValueNull(); + } +} diff --git a/src/main/java/com/caoccao/javet/interop/proxy/IJavetProxyHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/IJavetProxyHandler.java index 912ebde5e..1abaa613b 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/IJavetProxyHandler.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/IJavetProxyHandler.java @@ -17,31 +17,79 @@ package com.caoccao.javet.interop.proxy; import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interop.V8Runtime; import com.caoccao.javet.values.V8Value; import com.caoccao.javet.values.primitive.V8ValueBoolean; import com.caoccao.javet.values.reference.V8ValueArray; +import com.caoccao.javet.values.reference.V8ValueObject; /** * The interface Javet proxy handler. *

    - * https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Proxy + * Please refer to this doc + * for more details. * * @param the type parameter + * @param the type parameter * @since 0.9.6 */ -public interface IJavetProxyHandler { +public interface IJavetProxyHandler { /** - * Apply to object + * The constant FUNCTION_NAME_TO_V8_VALUE. + * + * @since 1.0.4 + */ + String FUNCTION_NAME_TO_V8_VALUE = "toV8Value"; + /** + * The constant PROXY_FUNCTION_NAME_APPLY. + * + * @since 2.2.0 + */ + String PROXY_FUNCTION_NAME_APPLY = "apply"; + /** + * The constant PROXY_FUNCTION_NAME_CONSTRUCT. + * + * @since 2.2.0 + */ + String PROXY_FUNCTION_NAME_CONSTRUCT = "construct"; + /** + * The constant PROXY_FUNCTION_NAME_GET. + * + * @since 2.2.0 + */ + String PROXY_FUNCTION_NAME_GET = "get"; + /** + * The constant PROXY_FUNCTION_NAME_HAS. + * + * @since 2.2.0 + */ + String PROXY_FUNCTION_NAME_HAS = "has"; + /** + * The constant PROXY_FUNCTION_NAME_OWN_KEYS. + * + * @since 2.2.0 + */ + String PROXY_FUNCTION_NAME_OWN_KEYS = "ownKeys"; + /** + * The constant PROXY_FUNCTION_NAME_SET. + * + * @since 2.2.0 + */ + String PROXY_FUNCTION_NAME_SET = "set"; + + /** + * Apply to object. * * @param target the target * @param thisObject this object * @param arguments the arguments * @return the V8 value * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8Value apply(V8Value target, V8Value thisObject, V8ValueArray arguments) throws JavetException { - throw new RuntimeException("Not implemented"); + default V8Value apply(V8Value target, V8Value thisObject, V8ValueArray arguments) throws JavetException, E { + return getV8Runtime().createV8ValueUndefined(); } /** @@ -52,21 +100,46 @@ default V8Value apply(V8Value target, V8Value thisObject, V8ValueArray arguments * @param newTarget the new target * @return the V8 value * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8Value construct(V8Value target, V8ValueArray arguments, V8Value newTarget) throws JavetException { - throw new RuntimeException("Not implemented"); + default V8Value construct(V8Value target, V8ValueArray arguments, V8Value newTarget) throws JavetException, E { + return getV8Runtime().createV8ValueUndefined(); } -// TODO: -// default V8ValueBoolean defineProperty(V8Value target, V8Value property, V8PropertyDescriptor descriptor) throws JavetException { -// throw new RuntimeException("Not implemented"); -// } + /** + * Define property. + * + * @param target the target + * @param property the property + * @param descriptor the descriptor + * @return the V8 value boolean + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8ValueBoolean defineProperty( + V8Value target, V8Value property, V8ValueObject descriptor) + throws JavetException, E { + return getV8Runtime().createV8ValueBoolean(false); + } -// TODO: -// default V8ValueBoolean deleteProperty(V8Value target, V8Value property, V8PropertyDescriptor descriptor) throws JavetException { -// throw new RuntimeException("Not implemented"); -// } + /** + * Delete property. + * + * @param target the target + * @param property the property + * @param descriptor the descriptor + * @return the V8 value boolean + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8ValueBoolean deleteProperty( + V8Value target, V8Value property, V8ValueObject descriptor) + throws JavetException, E { + return getV8Runtime().createV8ValueBoolean(false); + } /** * Get by property. @@ -76,16 +149,26 @@ default V8Value construct(V8Value target, V8ValueArray arguments, V8Value newTar * @param receiver the receiver * @return the V8 value * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8Value get(V8Value target, V8Value property, V8Value receiver) throws JavetException { - throw new RuntimeException("Not implemented"); + default V8Value get(V8Value target, V8Value property, V8Value receiver) throws JavetException, E { + return getV8Runtime().createV8ValueUndefined(); } -// TODO: -// default V8PropertyDescriptor getOwnPropertyDescriptor(V8Value target, V8Value property) throws JavetException { -// throw new RuntimeException("Not implemented"); -// } + /** + * Gets own property descriptor. + * + * @param target the target + * @param property the property + * @return the own property descriptor + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default V8ValueObject getOwnPropertyDescriptor(V8Value target, V8Value property) throws JavetException, E { + return getV8Runtime().createV8ValueObject(); + } /** * Gets prototype of. @@ -93,10 +176,11 @@ default V8Value get(V8Value target, V8Value property, V8Value receiver) throws J * @param target the target * @return the prototype of * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8Value getPrototypeOf(V8Value target) throws JavetException { - throw new RuntimeException("Not implemented"); + default V8Value getPrototypeOf(V8Value target) throws JavetException, E { + return getV8Runtime().createV8ValueUndefined(); } /** @@ -107,6 +191,14 @@ default V8Value getPrototypeOf(V8Value target) throws JavetException { */ T getTargetObject(); + /** + * Gets V8 runtime. + * + * @return the V8 runtime + * @since 2.2.0 + */ + V8Runtime getV8Runtime(); + /** * Has property * @@ -114,10 +206,11 @@ default V8Value getPrototypeOf(V8Value target) throws JavetException { * @param property the property * @return the V8 value boolean * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8ValueBoolean has(V8Value target, V8Value property) throws JavetException { - throw new RuntimeException("Not implemented"); + default V8ValueBoolean has(V8Value target, V8Value property) throws JavetException, E { + return getV8Runtime().createV8ValueBoolean(false); } /** @@ -126,22 +219,24 @@ default V8ValueBoolean has(V8Value target, V8Value property) throws JavetExcepti * @param target the target * @return the V8 value boolean * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8ValueBoolean isExtensible(V8Value target) throws JavetException { - throw new RuntimeException("Not implemented"); + default V8ValueBoolean isExtensible(V8Value target) throws JavetException, E { + return getV8Runtime().createV8ValueBoolean(false); } /** - * Own keys V8 value. + * Own keys. * * @param target the target - * @return the V8 value + * @return the V8 value array * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8Value ownKeys(V8Value target) throws JavetException { - throw new RuntimeException("Not implemented"); + default V8ValueArray ownKeys(V8Value target) throws JavetException, E { + return getV8Runtime().createV8ValueArray(); } /** @@ -150,10 +245,11 @@ default V8Value ownKeys(V8Value target) throws JavetException { * @param target the target * @return the V8 value boolean * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8ValueBoolean preventExtensions(V8Value target) throws JavetException { - throw new RuntimeException("Not implemented"); + default V8ValueBoolean preventExtensions(V8Value target) throws JavetException, E { + return getV8Runtime().createV8ValueBoolean(false); } /** @@ -165,11 +261,13 @@ default V8ValueBoolean preventExtensions(V8Value target) throws JavetException { * @param receiver the receiver * @return the V8 value boolean * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8ValueBoolean set(V8Value target, V8Value propertyKey, V8Value propertyValue, V8Value receiver) - throws JavetException { - throw new RuntimeException("Not implemented"); + default V8ValueBoolean set( + V8Value target, V8Value propertyKey, V8Value propertyValue, V8Value receiver) + throws JavetException, E { + return getV8Runtime().createV8ValueBoolean(false); } /** @@ -179,9 +277,10 @@ default V8ValueBoolean set(V8Value target, V8Value propertyKey, V8Value property * @param prototype the prototype * @return the V8 value boolean * @throws JavetException the javet exception + * @throws E the custom exception * @since 0.9.6 */ - default V8ValueBoolean setPrototypeOf(V8Value target, V8Value prototype) throws JavetException { - throw new RuntimeException("Not implemented"); + default V8ValueBoolean setPrototypeOf(V8Value target, V8Value prototype) throws JavetException, E { + return getV8Runtime().createV8ValueBoolean(false); } } diff --git a/src/main/java/com/caoccao/javet/interop/proxy/IJavetDynamicObjectFactory.java b/src/main/java/com/caoccao/javet/interop/proxy/IJavetReflectionObjectFactory.java similarity index 88% rename from src/main/java/com/caoccao/javet/interop/proxy/IJavetDynamicObjectFactory.java rename to src/main/java/com/caoccao/javet/interop/proxy/IJavetReflectionObjectFactory.java index e9d9c35ac..e1eaa21f1 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/IJavetDynamicObjectFactory.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/IJavetReflectionObjectFactory.java @@ -21,13 +21,13 @@ import com.caoccao.javet.values.reference.V8ValueProxy; /** - * The interface Javet dynamic object factory. + * The interface Javet reflection object factory. * * @since 2.0.1 */ -public interface IJavetDynamicObjectFactory { +public interface IJavetReflectionObjectFactory { /** - * Is dynamic object conversion supported. + * Is reflection object conversion supported. * * @param type the type to be converted * @param v8Value the V8 value @@ -43,7 +43,7 @@ default boolean isSupported(Class type, V8Value v8Value) { } /** - * Convert from V8 value to a dynamic object. + * Convert from V8 value to a reflection object. * * @param type the type to be converted * @param v8Value the V8 value diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetDirectProxyFunctionHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetDirectProxyFunctionHandler.java new file mode 100644 index 000000000..723c7f2e2 --- /dev/null +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetDirectProxyFunctionHandler.java @@ -0,0 +1,71 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interop.proxy; + +import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; +import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.reference.V8ValueArray; + +/** + * The type Javet direct proxy object handler. + * + * @param the type parameter + * @param the type parameter + * @since 2.2.0 + */ +public class JavetDirectProxyFunctionHandler, E extends Exception> + extends JavetDirectProxyObjectHandler { + /** + * Instantiates a new Base javet direct proxy object handler. + * + * @param v8Runtime the V8 runtime + * @param targetObject the target object + * @since 2.2.0 + */ + public JavetDirectProxyFunctionHandler(V8Runtime v8Runtime, T targetObject) { + super(v8Runtime, targetObject); + } + + @Override + public V8Value apply(V8Value target, V8Value thisObject, V8ValueArray arguments) throws JavetException, E { + return targetObject.proxyApply(target, thisObject, arguments); + } + + @Override + public JavetCallbackContext[] getCallbackContexts() { + return new JavetCallbackContext[]{ + new JavetCallbackContext( + PROXY_FUNCTION_NAME_APPLY, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> apply(v8Values[0], v8Values[1], (V8ValueArray) v8Values[2])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_GET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> get(v8Values[0], v8Values[1], v8Values[2])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_HAS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> has(v8Values[0], v8Values[1])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_OWN_KEYS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> ownKeys(v8Values[0])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_SET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> set(v8Values[0], v8Values[1], v8Values[2], v8Values[3])), + }; + } +} diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetDirectProxyObjectHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetDirectProxyObjectHandler.java new file mode 100644 index 000000000..cf5da16c1 --- /dev/null +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetDirectProxyObjectHandler.java @@ -0,0 +1,89 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interop.proxy; + +import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; +import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.primitive.V8ValueBoolean; +import com.caoccao.javet.values.reference.V8ValueArray; + +/** + * The type Javet direct proxy object handler. + * + * @param the type parameter + * @param the type parameter + * @since 2.2.0 + */ +public class JavetDirectProxyObjectHandler, E extends Exception> + extends BaseJavetDirectProxyHandler { + /** + * Instantiates a new Base javet direct proxy object handler. + * + * @param v8Runtime the V8 runtime + * @param targetObject the target object + * @since 2.2.0 + */ + public JavetDirectProxyObjectHandler(V8Runtime v8Runtime, T targetObject) { + super(v8Runtime, targetObject); + } + + @Override + public V8Value get(V8Value target, V8Value property, V8Value receiver) throws JavetException, E { + return targetObject.proxyGet(target, property, receiver); + } + + @Override + public JavetCallbackContext[] getCallbackContexts() { + return new JavetCallbackContext[]{ + new JavetCallbackContext( + PROXY_FUNCTION_NAME_GET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> get(v8Values[0], v8Values[1], v8Values[2])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_HAS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> has(v8Values[0], v8Values[1])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_OWN_KEYS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> ownKeys(v8Values[0])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_SET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> set(v8Values[0], v8Values[1], v8Values[2], v8Values[3])), + }; + } + + @Override + public V8ValueBoolean has(V8Value target, V8Value property) throws JavetException, E { + return targetObject.proxyHas(target, property); + } + + @Override + public V8ValueArray ownKeys(V8Value target) throws JavetException, E { + return targetObject.proxyOwnKeys(target); + } + + @Override + public V8ValueBoolean set( + V8Value target, + V8Value propertyKey, + V8Value propertyValue, + V8Value receiver) + throws JavetException, E { + return targetObject.proxySet(target, propertyKey, propertyValue, receiver); + } +} diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetProxySymbolToPrimitiveConverter.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetProxySymbolToPrimitiveConverter.java index bbcf4e649..8097a9a01 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/JavetProxySymbolToPrimitiveConverter.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetProxySymbolToPrimitiveConverter.java @@ -66,7 +66,7 @@ public JavetProxySymbolToPrimitiveConverter(V8Runtime v8Runtime, T targetObject) @Override public V8Value toV8Value(V8Value... v8Values) throws JavetException { - if (targetObject != null && v8Values.length > 0) { + if (targetObject != null && v8Values != null && v8Values.length > 0) { if (v8Values[0] instanceof V8ValueString) { String hintString = ((V8ValueString) v8Values[0]).getValue(); if (HINT_NUMBER.equals(hintString)) { diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyClassHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyClassHandler.java similarity index 69% rename from src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyClassHandler.java rename to src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyClassHandler.java index a683d90b9..369f0e7eb 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyClassHandler.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyClassHandler.java @@ -16,13 +16,14 @@ package com.caoccao.javet.interop.proxy; -import com.caoccao.javet.annotations.V8Function; import com.caoccao.javet.enums.V8ConversionMode; import com.caoccao.javet.enums.V8ProxyMode; import com.caoccao.javet.exceptions.JavetError; import com.caoccao.javet.exceptions.JavetException; import com.caoccao.javet.interop.V8Runtime; import com.caoccao.javet.interop.binding.ClassDescriptor; +import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; import com.caoccao.javet.utils.JavetResourceUtils; import com.caoccao.javet.utils.SimpleMap; import com.caoccao.javet.utils.ThreadSafeMap; @@ -33,12 +34,13 @@ import com.caoccao.javet.values.reference.V8ValueObject; /** - * The type Javet dynamic proxy class handler. + * The type Javet reflection proxy class handler. * * @param the type parameter * @since 1.1.7 */ -public class JavetDynamicProxyClassHandler> extends BaseJavetProxyHandler { +public class JavetReflectionProxyClassHandler, E extends Exception> + extends BaseJavetReflectionProxyHandler { /** * The constant METHOD_NAME_CONSTRUCTOR. * @@ -53,21 +55,20 @@ public class JavetDynamicProxyClassHandler> extends BaseJavet protected static final ThreadSafeMap, ClassDescriptor> classDescriptorMap = new ThreadSafeMap<>(); /** - * Instantiates a new Javet dynamic proxy handler. + * Instantiates a new Javet reflection proxy handler. * - * @param v8Runtime the V8 runtime - * @param dynamicObjectFactory the dynamic object factory - * @param targetObject the target object + * @param v8Runtime the V8 runtime + * @param reflectionObjectFactory the reflection object factory + * @param targetObject the target object * @since 0.9.6 */ - public JavetDynamicProxyClassHandler( + public JavetReflectionProxyClassHandler( V8Runtime v8Runtime, - IJavetDynamicObjectFactory dynamicObjectFactory, + IJavetReflectionObjectFactory reflectionObjectFactory, T targetObject) { - super(v8Runtime, dynamicObjectFactory, targetObject); + super(v8Runtime, reflectionObjectFactory, targetObject); } - @V8Function @Override public V8Value construct(V8Value target, V8ValueArray arguments, V8Value newTarget) throws JavetException { if (!classDescriptor.getConstructors().isEmpty()) { @@ -75,7 +76,7 @@ public V8Value construct(V8Value target, V8ValueArray arguments, V8Value newTarg try { v8Values = arguments.toArray(); return v8Runtime.toV8Value(execute( - dynamicObjectFactory, + reflectionObjectFactory, null, (V8ValueObject) target, classDescriptor.getConstructors(), @@ -89,14 +90,13 @@ public V8Value construct(V8Value target, V8ValueArray arguments, V8Value newTarg JavetError.PARAMETER_MESSAGE, t.getMessage()), t); } finally { if (v8Values != null) { - JavetResourceUtils.safeClose((Object[]) v8Values); + JavetResourceUtils.safeClose(v8Values); } } } return v8Runtime.createV8ValueUndefined(); } - @V8Function @Override public V8Value get(V8Value target, V8Value property, V8Value receiver) throws JavetException { V8Value result = getFromField(property); @@ -105,12 +105,35 @@ public V8Value get(V8Value target, V8Value property, V8Value receiver) throws Ja return result == null ? v8Runtime.createV8ValueUndefined() : result; } + @Override + public JavetCallbackContext[] getCallbackContexts() { + if (callbackContexts == null) { + callbackContexts = new JavetCallbackContext[]{ + new JavetCallbackContext( + PROXY_FUNCTION_NAME_CONSTRUCT, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> construct(v8Values[0], (V8ValueArray) v8Values[1], v8Values[2])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_GET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> get(v8Values[0], v8Values[1], v8Values[2])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_HAS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> has(v8Values[0], v8Values[1])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_OWN_KEYS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> ownKeys(v8Values[0])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_SET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> set(v8Values[0], v8Values[1], v8Values[2], v8Values[3])), + }; + } + return callbackContexts; + } + @Override public ThreadSafeMap, ClassDescriptor> getClassDescriptorCache() { return classDescriptorMap; } - @V8Function @Override public V8ValueBoolean has(V8Value target, V8Value property) throws JavetException { boolean isFound = hasFromRegular(property); @@ -152,13 +175,11 @@ protected void initializeFieldsAndMethods(Class currentClass, boolean staticM } while (currentClass != null); } - @V8Function @Override - public V8Value ownKeys(V8Value target) throws JavetException { + public V8ValueArray ownKeys(V8Value target) throws JavetException { return v8Runtime.toV8Value(classDescriptor.getUniqueKeySet().toArray()); } - @V8Function @Override public V8ValueBoolean set( V8Value target, diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyFactory.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyFactory.java similarity index 71% rename from src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyFactory.java rename to src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyFactory.java index e695ec1c7..680c5bd3e 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyFactory.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyFactory.java @@ -22,17 +22,18 @@ import com.caoccao.javet.values.reference.V8ValueObject; import com.caoccao.javet.values.reference.V8ValueProxy; +import java.lang.reflect.InvocationHandler; import java.lang.reflect.Proxy; /** - * The type Javet dynamic proxy factory. + * The type Javet reflection proxy factory. * * @since 2.0.1 */ -public final class JavetDynamicProxyFactory { - private static final JavetDynamicProxyFactory instance = new JavetDynamicProxyFactory(); +public final class JavetReflectionProxyFactory { + private static final JavetReflectionProxyFactory instance = new JavetReflectionProxyFactory(); - private JavetDynamicProxyFactory() { + private JavetReflectionProxyFactory() { } /** @@ -40,12 +41,12 @@ private JavetDynamicProxyFactory() { * * @return the instance */ - public static JavetDynamicProxyFactory getInstance() { + public static JavetReflectionProxyFactory getInstance() { return instance; } /** - * Is dynamic proxied function conversion supported. + * Is reflection proxied function conversion supported. * * @param type the type to be converted * @param v8Value the V8 value @@ -57,7 +58,7 @@ public boolean isSupportedFunction(Class type, V8Value v8Value) { } /** - * Is dynamic proxied object conversion supported. + * Is reflection proxied object conversion supported. * * @param type the type to be converted * @param v8Value the V8 value @@ -72,7 +73,7 @@ public boolean isSupportedObject(Class type, V8Value v8Value) { } /** - * Convert from V8 value to a dynamic proxied object. + * Convert from V8 value to a reflection proxied object. * * @param type the type to be converted * @param v8Value the V8 value @@ -82,16 +83,13 @@ public boolean isSupportedObject(Class type, V8Value v8Value) { */ public Object toObject(Class type, V8Value v8Value) throws JavetException { if (type.isInterface()) { + InvocationHandler invocationHandler = null; if (v8Value instanceof V8ValueFunction) { - JavetDynamicProxyV8ValueFunctionInvocationHandler invocationHandler = - new JavetDynamicProxyV8ValueFunctionInvocationHandler(v8Value.toClone()); - return Proxy.newProxyInstance( - getClass().getClassLoader(), - new Class[]{type, AutoCloseable.class}, - invocationHandler); + invocationHandler = new JavetReflectionProxyV8ValueFunctionInvocationHandler(v8Value.toClone()); } else if (v8Value instanceof V8ValueObject && !(v8Value instanceof V8ValueProxy)) { - JavetDynamicProxyV8ValueObjectInvocationHandler invocationHandler = - new JavetDynamicProxyV8ValueObjectInvocationHandler(v8Value.toClone()); + invocationHandler = new JavetReflectionProxyV8ValueObjectInvocationHandler(v8Value.toClone()); + } + if (invocationHandler != null) { return Proxy.newProxyInstance( getClass().getClassLoader(), new Class[]{type, AutoCloseable.class}, diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyFunctionHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyFunctionHandler.java similarity index 50% rename from src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyFunctionHandler.java rename to src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyFunctionHandler.java index 5e10a5b12..ce74f4743 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyFunctionHandler.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyFunctionHandler.java @@ -16,10 +16,11 @@ package com.caoccao.javet.interop.proxy; -import com.caoccao.javet.annotations.V8Function; import com.caoccao.javet.exceptions.JavetError; import com.caoccao.javet.exceptions.JavetException; import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; import com.caoccao.javet.utils.JavetResourceUtils; import com.caoccao.javet.utils.SimpleMap; import com.caoccao.javet.utils.V8ValueUtils; @@ -27,12 +28,14 @@ import com.caoccao.javet.values.reference.V8ValueArray; /** - * The type Javet dynamic proxy function handler. + * The type Javet reflection proxy function handler. * * @param the type parameter + * @param the type parameter * @since 1.1.7 */ -public class JavetDynamicProxyFunctionHandler extends JavetDynamicProxyObjectHandler { +public class JavetReflectionProxyFunctionHandler + extends JavetReflectionProxyObjectHandler { /** * The constant METHOD_NAME_APPLY. @@ -42,21 +45,20 @@ public class JavetDynamicProxyFunctionHandler extends JavetDynamicProxyObject protected static final String METHOD_NAME_APPLY = "apply"; /** - * Instantiates a new Javet dynamic proxy function handler. + * Instantiates a new Javet reflection proxy function handler. * - * @param v8Runtime the V8 runtime - * @param dynamicObjectFactory the dynamic object factory - * @param targetObject the target object + * @param v8Runtime the V8 runtime + * @param reflectionObjectFactory the reflection object factory + * @param targetObject the target object * @since 1.1.7 */ - public JavetDynamicProxyFunctionHandler( + public JavetReflectionProxyFunctionHandler( V8Runtime v8Runtime, - IJavetDynamicObjectFactory dynamicObjectFactory, + IJavetReflectionObjectFactory reflectionObjectFactory, T targetObject) { - super(v8Runtime, dynamicObjectFactory, targetObject); + super(v8Runtime, reflectionObjectFactory, targetObject); } - @V8Function @Override public V8Value apply(V8Value target, V8Value thisObject, V8ValueArray arguments) throws JavetException { if (!classDescriptor.getApplyFunctions().isEmpty()) { @@ -64,7 +66,7 @@ public V8Value apply(V8Value target, V8Value thisObject, V8ValueArray arguments) try { v8Values = arguments.toArray(); return v8Runtime.toV8Value(execute( - dynamicObjectFactory, + reflectionObjectFactory, targetObject, null, classDescriptor.getApplyFunctions(), @@ -78,10 +80,34 @@ public V8Value apply(V8Value target, V8Value thisObject, V8ValueArray arguments) JavetError.PARAMETER_MESSAGE, t.getMessage()), t); } finally { if (v8Values != null) { - JavetResourceUtils.safeClose((Object[]) v8Values); + JavetResourceUtils.safeClose(v8Values); } } } return v8Runtime.createV8ValueUndefined(); } + + @Override + public JavetCallbackContext[] getCallbackContexts() { + if (callbackContexts == null) { + callbackContexts = new JavetCallbackContext[]{ + new JavetCallbackContext( + PROXY_FUNCTION_NAME_APPLY, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> apply(v8Values[0], v8Values[1], (V8ValueArray) v8Values[2])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_GET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> get(v8Values[0], v8Values[1], v8Values[2])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_HAS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> has(v8Values[0], v8Values[1])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_OWN_KEYS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> ownKeys(v8Values[0])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_SET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> set(v8Values[0], v8Values[1], v8Values[2], v8Values[3])), + }; + } + return callbackContexts; + } } diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyInterceptor.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyInterceptor.java similarity index 83% rename from src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyInterceptor.java rename to src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyInterceptor.java index 89b1526ef..00c515b06 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyInterceptor.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyInterceptor.java @@ -29,32 +29,32 @@ import java.util.List; /** - * The type Javet dynamic proxy interceptor. + * The type Javet reflection proxy interceptor. * * @since 0.9.6 */ -final class JavetDynamicProxyInterceptor { +final class JavetReflectionProxyInterceptor { private static final String METHOD_NAME_INVOKE = "invoke"; - private final IJavetDynamicObjectFactory dynamicObjectFactory; private final String jsMethodName; private final List methods; + private final IJavetReflectionObjectFactory reflectionObjectFactory; private final Object targetObject; /** - * Instantiates a new Javet dynamic proxy interceptor. + * Instantiates a new Javet reflection proxy interceptor. * - * @param dynamicObjectFactory the dynamic object factory - * @param targetObject the target object - * @param jsMethodName the JS method name - * @param methods the methods + * @param reflectionObjectFactory the reflection object factory + * @param targetObject the target object + * @param jsMethodName the JS method name + * @param methods the methods * @since 0.9.6 */ - public JavetDynamicProxyInterceptor( - IJavetDynamicObjectFactory dynamicObjectFactory, + public JavetReflectionProxyInterceptor( + IJavetReflectionObjectFactory reflectionObjectFactory, Object targetObject, String jsMethodName, List methods) { - this.dynamicObjectFactory = dynamicObjectFactory; + this.reflectionObjectFactory = reflectionObjectFactory; this.jsMethodName = jsMethodName; this.methods = methods; this.targetObject = targetObject; @@ -70,6 +70,7 @@ public JavetDynamicProxyInterceptor( public JavetCallbackContext getCallbackContext() { try { return new JavetCallbackContext( + METHOD_NAME_INVOKE, this, getClass().getMethod(METHOD_NAME_INVOKE, V8ValueObject.class, V8Value[].class), true); @@ -119,8 +120,8 @@ public Object getTargetObject() { */ public Object invoke(V8ValueObject thisObject, V8Value... v8Values) throws JavetException { try { - return BaseJavetProxyHandler.execute( - dynamicObjectFactory, + return BaseJavetReflectionProxyHandler.execute( + reflectionObjectFactory, targetObject, thisObject, methods, diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyObjectHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyObjectHandler.java similarity index 85% rename from src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyObjectHandler.java rename to src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyObjectHandler.java index 1ed4f5a14..22bc81ea9 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyObjectHandler.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyObjectHandler.java @@ -16,13 +16,14 @@ package com.caoccao.javet.interop.proxy; -import com.caoccao.javet.annotations.V8Function; import com.caoccao.javet.enums.V8ConversionMode; import com.caoccao.javet.enums.V8ProxyMode; import com.caoccao.javet.exceptions.JavetException; import com.caoccao.javet.interop.V8Runtime; import com.caoccao.javet.interop.V8Scope; import com.caoccao.javet.interop.binding.ClassDescriptor; +import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; import com.caoccao.javet.utils.JavetStringUtils; import com.caoccao.javet.utils.ThreadSafeMap; import com.caoccao.javet.values.V8Value; @@ -36,13 +37,15 @@ import java.util.*; /** - * The type Javet dynamic proxy object handler. + * The type Javet reflection proxy object handler. * * @param the type parameter + * @param the type parameter * @since 0.9.6 */ @SuppressWarnings("unchecked") -public class JavetDynamicProxyObjectHandler extends BaseJavetProxyHandler { +public class JavetReflectionProxyObjectHandler + extends BaseJavetReflectionProxyHandler { /** * The constant FUNCTION_NAME_LENGTH. @@ -58,21 +61,20 @@ public class JavetDynamicProxyObjectHandler extends BaseJavetProxyHandler protected static final ThreadSafeMap, ClassDescriptor> classDescriptorMap = new ThreadSafeMap<>(); /** - * Instantiates a new Javet dynamic proxy object handler. + * Instantiates a new Javet reflection proxy object handler. * - * @param v8Runtime the V8 runtime - * @param dynamicObjectFactory the dynamic object factory - * @param targetObject the target object + * @param v8Runtime the V8 runtime + * @param reflectionObjectFactory the reflection object factory + * @param targetObject the target object * @since 0.9.6 */ - public JavetDynamicProxyObjectHandler( + public JavetReflectionProxyObjectHandler( V8Runtime v8Runtime, - IJavetDynamicObjectFactory dynamicObjectFactory, + IJavetReflectionObjectFactory reflectionObjectFactory, T targetObject) { - super(v8Runtime, dynamicObjectFactory, Objects.requireNonNull(targetObject)); + super(v8Runtime, reflectionObjectFactory, Objects.requireNonNull(targetObject)); } - @V8Function @Override public V8Value get(V8Value target, V8Value property, V8Value receiver) throws JavetException { V8Value result = getFromCollection(property); @@ -83,6 +85,27 @@ public V8Value get(V8Value target, V8Value property, V8Value receiver) throws Ja return result == null ? v8Runtime.createV8ValueUndefined() : result; } + @Override + public JavetCallbackContext[] getCallbackContexts() { + if (callbackContexts == null) { + callbackContexts = new JavetCallbackContext[]{ + new JavetCallbackContext( + PROXY_FUNCTION_NAME_GET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> get(v8Values[0], v8Values[1], v8Values[2])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_HAS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> has(v8Values[0], v8Values[1])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_OWN_KEYS, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> ownKeys(v8Values[0])), + new JavetCallbackContext( + PROXY_FUNCTION_NAME_SET, this, JavetCallbackType.DirectCallNoThisAndResult, + (NoThisAndResult) (v8Values) -> set(v8Values[0], v8Values[1], v8Values[2], v8Values[3])), + }; + } + return callbackContexts; + } + @Override public ThreadSafeMap, ClassDescriptor> getClassDescriptorCache() { return classDescriptorMap; @@ -142,7 +165,6 @@ protected V8Value getFromSymbol(V8Value property) throws JavetException { return null; } - @V8Function @Override public V8ValueBoolean has(V8Value target, V8Value property) throws JavetException { boolean isFound = hasFromCollection(property); @@ -232,9 +254,8 @@ protected void initializeFieldsAndMethods(Class currentClass, boolean staticM } while (currentClass != null); } - @V8Function @Override - public V8Value ownKeys(V8Value target) throws JavetException { + public V8ValueArray ownKeys(V8Value target) throws JavetException { Object[] keys = null; if (classDescriptor.isTargetTypeMap()) { keys = ((Map) targetObject).keySet().toArray(); @@ -269,7 +290,6 @@ public V8Value ownKeys(V8Value target) throws JavetException { return v8Runtime.toV8Value(classDescriptor.getUniqueKeySet().toArray()); } - @V8Function @Override public V8ValueBoolean set( V8Value target, diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyV8ValueFunctionInvocationHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyV8ValueFunctionInvocationHandler.java similarity index 84% rename from src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyV8ValueFunctionInvocationHandler.java rename to src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyV8ValueFunctionInvocationHandler.java index e63e5d506..ae9332af7 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyV8ValueFunctionInvocationHandler.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyV8ValueFunctionInvocationHandler.java @@ -25,21 +25,21 @@ import java.lang.reflect.Method; /** - * The type Javet dynamic proxy V8 value function invocation handler. + * The type Javet reflection proxy V8 value function invocation handler. * * @since 0.9.10 */ -public final class JavetDynamicProxyV8ValueFunctionInvocationHandler implements InvocationHandler, IJavetClosable { +public final class JavetReflectionProxyV8ValueFunctionInvocationHandler implements InvocationHandler, IJavetClosable { private static final String METHOD_NAME_CLOSE = "close"; private V8ValueFunction v8ValueFunction; /** - * Instantiates a new Javet dynamic proxy V8 value function invocation handler. + * Instantiates a new Javet reflection proxy V8 value function invocation handler. * * @param v8ValueFunction the V8 value function * @since 0.9.10 */ - public JavetDynamicProxyV8ValueFunctionInvocationHandler(V8ValueFunction v8ValueFunction) { + public JavetReflectionProxyV8ValueFunctionInvocationHandler(V8ValueFunction v8ValueFunction) { this.v8ValueFunction = v8ValueFunction; } diff --git a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyV8ValueObjectInvocationHandler.java b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyV8ValueObjectInvocationHandler.java similarity index 86% rename from src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyV8ValueObjectInvocationHandler.java rename to src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyV8ValueObjectInvocationHandler.java index ff4ec9696..f54a79158 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/JavetDynamicProxyV8ValueObjectInvocationHandler.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/JavetReflectionProxyV8ValueObjectInvocationHandler.java @@ -26,21 +26,21 @@ import java.lang.reflect.Method; /** - * The type Javet dynamic proxy V8 value object invocation handler. + * The type Javet reflection proxy V8 value object invocation handler. * * @since 0.9.10 */ -public final class JavetDynamicProxyV8ValueObjectInvocationHandler implements InvocationHandler, IJavetClosable { +public final class JavetReflectionProxyV8ValueObjectInvocationHandler implements InvocationHandler, IJavetClosable { private static final String METHOD_NAME_CLOSE = "close"; private V8ValueObject v8ValueObject; /** - * Instantiates a new Javet dynamic proxy V8 value object invocation handler. + * Instantiates a new Javet reflection proxy V8 value object invocation handler. * * @param v8ValueObject the V8 value object * @since 0.9.10 */ - public JavetDynamicProxyV8ValueObjectInvocationHandler(V8ValueObject v8ValueObject) { + public JavetReflectionProxyV8ValueObjectInvocationHandler(V8ValueObject v8ValueObject) { this.v8ValueObject = v8ValueObject; } diff --git a/src/main/java/com/caoccao/javet/interop/proxy/ScoredExecutable.java b/src/main/java/com/caoccao/javet/interop/proxy/ScoredExecutable.java index 757aa4f9e..244d75a80 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/ScoredExecutable.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/ScoredExecutable.java @@ -60,8 +60,8 @@ final class ScoredExecutable { * @since 0.9.10 */ private static final Class V8_VALUE_PROXY_CLASS = V8ValueProxy.class; - private final IJavetDynamicObjectFactory dynamicObjectFactory; private final E executable; + private final IJavetReflectionObjectFactory reflectionObjectFactory; private final Object targetObject; private final V8ValueObject thisObject; private JavetVirtualObject[] javetVirtualObjects; @@ -70,21 +70,21 @@ final class ScoredExecutable { /** * Instantiates a new Scored executable. * - * @param dynamicObjectFactory the dynamic object factory - * @param targetObject the target object - * @param thisObject this object - * @param executable the executable - * @param javetVirtualObjects the javet virtual objects + * @param reflectionObjectFactory the reflection object factory + * @param targetObject the target object + * @param thisObject this object + * @param executable the executable + * @param javetVirtualObjects the javet virtual objects * @since 0.9.10 */ public ScoredExecutable( - IJavetDynamicObjectFactory dynamicObjectFactory, + IJavetReflectionObjectFactory reflectionObjectFactory, Object targetObject, V8ValueObject thisObject, E executable, JavetVirtualObject[] javetVirtualObjects) { this.executable = executable; - this.dynamicObjectFactory = dynamicObjectFactory; + this.reflectionObjectFactory = reflectionObjectFactory; this.javetVirtualObjects = javetVirtualObjects; this.score = 0; this.targetObject = targetObject; @@ -139,7 +139,7 @@ public void calculateScore() throws JavetException { if (isVarArgs || isFixedArgs) { double totalScore = 0; final int fixedParameterCount = isExecutableVarArgs ? parameterCount - 1 : parameterCount; - final JavetDynamicProxyFactory dynamicProxyFactory = JavetDynamicProxyFactory.getInstance(); + final JavetReflectionProxyFactory reflectionProxyFactory = JavetReflectionProxyFactory.getInstance(); for (int i = 0; i < fixedParameterCount; i++) { Class parameterType = parameterTypes[i]; final V8Value v8Value = javetVirtualObjects[i].getV8Value(); @@ -152,13 +152,13 @@ public void calculateScore() throws JavetException { } else if (object != null && parameterType.isAssignableFrom(object.getClass())) { totalScore += 0.9; continue; - } else if (dynamicProxyFactory.isSupportedFunction(parameterType, v8Value)) { + } else if (reflectionProxyFactory.isSupportedFunction(parameterType, v8Value)) { totalScore += 0.95; continue; - } else if (dynamicProxyFactory.isSupportedObject(parameterType, v8Value)) { + } else if (reflectionProxyFactory.isSupportedObject(parameterType, v8Value)) { totalScore += 0.85; continue; - } else if (dynamicObjectFactory != null && dynamicObjectFactory.isSupported(parameterType, v8Value)) { + } else if (reflectionObjectFactory != null && reflectionObjectFactory.isSupported(parameterType, v8Value)) { totalScore += 0.5; continue; } @@ -194,13 +194,13 @@ public void calculateScore() throws JavetException { } else if (object != null && componentType.isAssignableFrom(object.getClass())) { totalScore += 0.85; continue; - } else if (dynamicProxyFactory.isSupportedFunction(componentType, v8Value)) { + } else if (reflectionProxyFactory.isSupportedFunction(componentType, v8Value)) { totalScore += 0.95; continue; - } else if (dynamicProxyFactory.isSupportedObject(componentType, v8Value)) { + } else if (reflectionProxyFactory.isSupportedObject(componentType, v8Value)) { totalScore += 0.85; continue; - } else if (dynamicObjectFactory != null && dynamicObjectFactory.isSupported(componentType, v8Value)) { + } else if (reflectionObjectFactory != null && reflectionObjectFactory.isSupported(componentType, v8Value)) { totalScore += 0.5; continue; } @@ -277,7 +277,7 @@ public Object execute() throws Throwable { } else { List parameters = new ArrayList<>(); final int fixedParameterCount = isExecutableVarArgs ? parameterCount - 1 : parameterCount; - final JavetDynamicProxyFactory dynamicProxyFactory = JavetDynamicProxyFactory.getInstance(); + final JavetReflectionProxyFactory reflectionProxyFactory = JavetReflectionProxyFactory.getInstance(); for (int i = 0; i < fixedParameterCount; i++) { Class parameterType = parameterTypes[i]; final V8Value v8Value = javetVirtualObjects[i].getV8Value(); @@ -291,12 +291,12 @@ public Object execute() throws Throwable { conversionRequired = false; } else if (object != null && parameterType.isAssignableFrom(object.getClass())) { conversionRequired = false; - } else if (dynamicProxyFactory.isSupportedFunction(parameterType, v8Value) - || dynamicProxyFactory.isSupportedObject(parameterType, v8Value)) { - parameter = dynamicProxyFactory.toObject(parameterType, v8Value); + } else if (reflectionProxyFactory.isSupportedFunction(parameterType, v8Value) + || reflectionProxyFactory.isSupportedObject(parameterType, v8Value)) { + parameter = reflectionProxyFactory.toObject(parameterType, v8Value); conversionRequired = false; - } else if (dynamicObjectFactory != null && dynamicObjectFactory.isSupported(parameterType, v8Value)) { - parameter = dynamicObjectFactory.toObject(parameterType, v8Value); + } else if (reflectionObjectFactory != null && reflectionObjectFactory.isSupported(parameterType, v8Value)) { + parameter = reflectionObjectFactory.toObject(parameterType, v8Value); conversionRequired = false; } } @@ -333,12 +333,12 @@ public Object execute() throws Throwable { conversionRequired = false; } else if (object != null && componentType.isAssignableFrom(object.getClass())) { conversionRequired = false; - } else if (dynamicProxyFactory.isSupportedFunction(componentType, v8Value) - || dynamicProxyFactory.isSupportedObject(componentType, v8Value)) { - parameter = dynamicProxyFactory.toObject(componentType, v8Value); + } else if (reflectionProxyFactory.isSupportedFunction(componentType, v8Value) + || reflectionProxyFactory.isSupportedObject(componentType, v8Value)) { + parameter = reflectionProxyFactory.toObject(componentType, v8Value); conversionRequired = false; - } else if (dynamicObjectFactory != null && dynamicObjectFactory.isSupported(componentType, v8Value)) { - parameter = dynamicObjectFactory.toObject(componentType, v8Value); + } else if (reflectionObjectFactory != null && reflectionObjectFactory.isSupported(componentType, v8Value)) { + parameter = reflectionObjectFactory.toObject(componentType, v8Value); conversionRequired = false; } } diff --git a/src/main/java/com/caoccao/javet/interop/proxy/package-info.java b/src/main/java/com/caoccao/javet/interop/proxy/package-info.java index e611c4cd8..eda2401d0 100644 --- a/src/main/java/com/caoccao/javet/interop/proxy/package-info.java +++ b/src/main/java/com/caoccao/javet/interop/proxy/package-info.java @@ -15,7 +15,7 @@ */ /** - * Dynamic proxy handlers for polyfilling Java interfaces with JS functions or objects. + * Reflection and direct proxy handlers for polyfilling Java interfaces with JS functions or objects. * * @since 0.7.0 * @author Sam Cao diff --git a/src/main/java/com/caoccao/javet/utils/JavetResourceUtils.java b/src/main/java/com/caoccao/javet/utils/JavetResourceUtils.java index 2964b8efb..b130ab352 100644 --- a/src/main/java/com/caoccao/javet/utils/JavetResourceUtils.java +++ b/src/main/java/com/caoccao/javet/utils/JavetResourceUtils.java @@ -58,6 +58,18 @@ public static void safeClose(Object... objects) { } } + /** + * Safe close. + * + * @param v8Values the V8 values + * @since 2.2.0 + */ + public static void safeClose(V8Value... v8Values) { + for (V8Value v8Value : v8Values) { + safeClose(v8Value); + } + } + /** * Safe close. * diff --git a/src/main/java/com/caoccao/javet/values/reference/IV8Cacheable.java b/src/main/java/com/caoccao/javet/values/reference/IV8Cacheable.java new file mode 100644 index 000000000..1692d88a1 --- /dev/null +++ b/src/main/java/com/caoccao/javet/values/reference/IV8Cacheable.java @@ -0,0 +1,35 @@ +/* + * Copyright (c) 2021-2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.values.reference; + +import com.caoccao.javet.exceptions.JavetException; + +/** + * The interface V8 cacheable. + * + * @since 2.2.0 + */ +public interface IV8Cacheable extends IV8ValueReference { + /** + * Gets cached data. + * + * @return the cached data + * @throws JavetException the javet exception + * @since 2.2.0 + */ + byte[] getCachedData() throws JavetException; +} diff --git a/src/main/java/com/caoccao/javet/values/reference/IV8Module.java b/src/main/java/com/caoccao/javet/values/reference/IV8Module.java index 544d2561d..a699b9f2a 100644 --- a/src/main/java/com/caoccao/javet/values/reference/IV8Module.java +++ b/src/main/java/com/caoccao/javet/values/reference/IV8Module.java @@ -22,7 +22,7 @@ import com.caoccao.javet.values.V8Value; @SuppressWarnings("unchecked") -public interface IV8Module extends IV8ValueReference, IV8Executable { +public interface IV8Module extends IV8Cacheable, IV8ValueReference, IV8Executable { int Uninstantiated = 0; int Instantiating = 1; int Instantiated = 2; @@ -52,8 +52,6 @@ default T execute(boolean resultRequired) throws JavetExcept return (T) getV8Runtime().createV8ValueUndefined(); } - byte[] getCachedData() throws JavetException; - @CheckReturnValue V8ValueError getException() throws JavetException; diff --git a/src/main/java/com/caoccao/javet/values/reference/IV8Script.java b/src/main/java/com/caoccao/javet/values/reference/IV8Script.java index 2b9644dc3..12ee3c649 100644 --- a/src/main/java/com/caoccao/javet/values/reference/IV8Script.java +++ b/src/main/java/com/caoccao/javet/values/reference/IV8Script.java @@ -21,9 +21,7 @@ import com.caoccao.javet.interop.IV8Executable; import com.caoccao.javet.values.V8Value; -public interface IV8Script extends IV8ValueReference, IV8Executable { - byte[] getCachedData() throws JavetException; - +public interface IV8Script extends IV8Cacheable, IV8ValueReference, IV8Executable { String getResourceName(); void setResourceName(String resourceName); diff --git a/src/main/java/com/caoccao/javet/values/reference/IV8ValueArray.java b/src/main/java/com/caoccao/javet/values/reference/IV8ValueArray.java index e2707882c..e82f9fd7d 100644 --- a/src/main/java/com/caoccao/javet/values/reference/IV8ValueArray.java +++ b/src/main/java/com/caoccao/javet/values/reference/IV8ValueArray.java @@ -18,16 +18,93 @@ import com.caoccao.javet.annotations.CheckReturnValue; import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interfaces.IJavetUniConsumer; +import com.caoccao.javet.interfaces.IJavetUniIndexedConsumer; +import com.caoccao.javet.utils.JavetResourceUtils; import com.caoccao.javet.values.V8Value; import com.caoccao.javet.values.primitive.V8ValueNull; import com.caoccao.javet.values.primitive.V8ValuePrimitive; import com.caoccao.javet.values.primitive.V8ValueUndefined; import java.math.BigInteger; +import java.util.Arrays; import java.util.List; +/** + * The interface V8 value array. + * + * @since 0.7.0 + */ @SuppressWarnings("unchecked") public interface IV8ValueArray extends IV8ValueObject { + /** + * Batch get the given range of items from the array. + * + * @param v8Values the V8 values + * @param startIndex the start index + * @param endIndex the end index + * @return the actual item count + * @throws JavetException the javet exception + * @since 2.2.0 + */ + int batchGet(V8Value[] v8Values, int startIndex, int endIndex) throws JavetException; + + /** + * Batch get all the items from the array. + * + * @param the type parameter + * @return the V8 values + * @throws JavetException the javet exception + * @since 2.2.0 + */ + default T[] batchGet() throws JavetException { + final int length = getLength(); + V8Value[] v8Values = new V8Value[length]; + if (length > 0) { + try { + batchGet(v8Values, 0, length); + } catch (Throwable t) { + JavetResourceUtils.safeClose(v8Values); + Arrays.fill(v8Values, null); + throw t; + } + } + return (T[]) v8Values; + } + + /** + * For each of the item, call the consumer and return the item count. + * + * @param the type parameter + * @param the type parameter + * @param consumer the consumer + * @param batchSize the batch size + * @return the item count + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + int forEach( + IJavetUniConsumer consumer, + int batchSize) + throws JavetException, E; + + /** + * For each of the item, call the consumer and return the item count. + * + * @param the type parameter + * @param the type parameter + * @param consumer the consumer + * @param batchSize the batch size + * @return the item count + * @throws JavetException the javet exception + * @throws E the custom exception + */ + int forEach( + IJavetUniIndexedConsumer consumer, + int batchSize) + throws JavetException, E; + @CheckReturnValue T get(int index) throws JavetException; @@ -90,7 +167,7 @@ default V8ValueUndefined popUndefined() throws JavetException { return pop(); } - int push(Object value) throws JavetException; + int push(Object... objects) throws JavetException; default int pushNull() throws JavetException { return push(getV8Runtime().createV8ValueNull()); @@ -102,11 +179,6 @@ default int pushUndefined() throws JavetException { @CheckReturnValue default V8Value[] toArray() throws JavetException { - final int length = getLength(); - V8Value[] v8Values = new V8Value[length]; - for (int i = 0; i < length; ++i) { - v8Values[i] = get(i); - } - return v8Values; + return batchGet(); } } diff --git a/src/main/java/com/caoccao/javet/values/reference/IV8ValueFunction.java b/src/main/java/com/caoccao/javet/values/reference/IV8ValueFunction.java index cfdbb83db..ef518e8a6 100644 --- a/src/main/java/com/caoccao/javet/values/reference/IV8ValueFunction.java +++ b/src/main/java/com/caoccao/javet/values/reference/IV8ValueFunction.java @@ -38,7 +38,7 @@ * @since 0.7.0 */ @SuppressWarnings("unchecked") -public interface IV8ValueFunction extends IV8ValueObject { +public interface IV8ValueFunction extends IV8Cacheable, IV8ValueObject { /** * Call a function by objects and return V8 value. @@ -342,15 +342,6 @@ default boolean copyContextFrom(IV8ValueFunction sourceIV8ValueFunction) throws */ String[] getArguments() throws JavetException; - /** - * Gets cached data from a function. - * - * @return the cached data - * @throws JavetException the javet exception - * @since 2.0.3 - */ - byte[] getCachedData() throws JavetException; - /** * Gets the V8 context. * diff --git a/src/main/java/com/caoccao/javet/values/reference/IV8ValueObject.java b/src/main/java/com/caoccao/javet/values/reference/IV8ValueObject.java index 2b2a3dfc3..63f9c29db 100644 --- a/src/main/java/com/caoccao/javet/values/reference/IV8ValueObject.java +++ b/src/main/java/com/caoccao/javet/values/reference/IV8ValueObject.java @@ -43,43 +43,53 @@ */ @SuppressWarnings("unchecked") public interface IV8ValueObject extends IV8ValueReference { + /** + * The constant DEFAULT_BATCH_SIZE is the default batch size for get a chunk of items. + * + * @since 2.2.0 + */ + int DEFAULT_BATCH_SIZE = 100; + /** + * The constant MIN_BATCH_SIZE. + * + * @since 2.2.0 + */ + int MIN_BATCH_SIZE = 1; /** - * Bind both functions via @V8Function and properties via @V8Property. + * Batch get a range of values by keys. * - * @param callbackReceiver the callback receiver - * @return the list of callback context + * @param v8ValueKeys the V8 value keys + * @param v8ValueValues the V8 value values + * @param length the length + * @return the actual item count * @throws JavetException the javet exception - * @since 0.8.9 */ - List bind(Object callbackReceiver) throws JavetException; + @SuppressWarnings("UnusedReturnValue") + int batchGet(V8Value[] v8ValueKeys, V8Value[] v8ValueValues, int length) throws JavetException; /** - * Binds function by name string and callback context. - *

    - * It is for creating a Java code based function in V8. + * Bind both functions via @V8Function and properties via @V8Property. * - * @param functionName the function name - * @param javetCallbackContext the javet callback context - * @return true : the function is bind, false: the function is not bind + * @param callbackReceiver the callback receiver + * @return the list of callback context * @throws JavetException the javet exception * @since 0.8.9 */ - @SuppressWarnings("UnusedReturnValue") - boolean bindFunction(String functionName, JavetCallbackContext javetCallbackContext) throws JavetException; + List bind(Object callbackReceiver) throws JavetException; /** * Binds function by name symbol and callback context. *

    * It is for creating a Java code based function in V8. * - * @param functionName the function name * @param javetCallbackContext the javet callback context * @return true : the function is bind, false: the function is not bind * @throws JavetException the javet exception - * @since 1.0.0 + * @since 2.2.0 */ - boolean bindFunction(V8ValueSymbol functionName, JavetCallbackContext javetCallbackContext) throws JavetException; + @SuppressWarnings("UnusedReturnValue") + boolean bindFunction(JavetCallbackContext javetCallbackContext) throws JavetException; /** * Binds function by name string and code string. @@ -134,73 +144,18 @@ default boolean bindFunction(V8ValueSymbol functionName, String codeString) thro /** * Bind property by name string and getter. * - * @param propertyName the property name * @param javetCallbackContextGetter the javet callback context getter * @return true : the property is bind, false : the property is not bind * @throws JavetException the javet exception * @since 0.8.9 */ - default boolean bindProperty( - String propertyName, - JavetCallbackContext javetCallbackContextGetter) throws JavetException { - return bindProperty(propertyName, javetCallbackContextGetter, null); + default boolean bindProperty(JavetCallbackContext javetCallbackContextGetter) throws JavetException { + return bindProperty(javetCallbackContextGetter, null); } /** - * Bind property by name string, getter and setter. + * Bind property by getter and setter. * - * @param propertyName the property name - * @param javetCallbackContextGetter the javet callback context getter - * @param javetCallbackContextSetter the javet callback context setter - * @return true : the property is bind, false : the property is not bind - * @throws JavetException the javet exception - * @since 0.9.11 - */ - default boolean bindProperty( - String propertyName, - JavetCallbackContext javetCallbackContextGetter, - JavetCallbackContext javetCallbackContextSetter) throws JavetException { - Objects.requireNonNull(propertyName); - return bindProperty( - getV8Runtime().createV8ValueString(propertyName), - javetCallbackContextGetter, - javetCallbackContextSetter); - } - - /** - * Bind property by name string and getter. - * - * @param propertyName the property name - * @param javetCallbackContextGetter the javet callback context getter - * @return true : the property is bind, false : the property is not bind - * @throws JavetException the javet exception - * @since 0.9.11 - */ - default boolean bindProperty( - V8ValueString propertyName, - JavetCallbackContext javetCallbackContextGetter) throws JavetException { - return bindProperty(propertyName, javetCallbackContextGetter, null); - } - - /** - * Bind property by name symbol and getter. - * - * @param propertyName the property name - * @param javetCallbackContextGetter the javet callback context getter - * @return true : the property is bind, false : the property is not bind - * @throws JavetException the javet exception - * @since 0.9.11 - */ - default boolean bindProperty( - V8ValueSymbol propertyName, - JavetCallbackContext javetCallbackContextGetter) throws JavetException { - return bindProperty(propertyName, javetCallbackContextGetter, null); - } - - /** - * Bind property by name string, getter and setter. - * - * @param propertyName the property name * @param javetCallbackContextGetter the javet callback context getter * @param javetCallbackContextSetter the javet callback context setter * @return true : the property is bind, false : the property is not bind @@ -208,24 +163,9 @@ default boolean bindProperty( * @since 0.8.9 */ boolean bindProperty( - V8ValueString propertyName, - JavetCallbackContext javetCallbackContextGetter, - JavetCallbackContext javetCallbackContextSetter) throws JavetException; - - /** - * Bind property by name symbol, getter and setter. - * - * @param propertyName the property name - * @param javetCallbackContextGetter the javet callback context getter - * @param javetCallbackContextSetter the javet callback context setter - * @return true : the property is bind, false : the property is not bind - * @throws JavetException the javet exception - * @since 0.9.11 - */ - boolean bindProperty( - V8ValueSymbol propertyName, JavetCallbackContext javetCallbackContextGetter, - JavetCallbackContext javetCallbackContextSetter) throws JavetException; + JavetCallbackContext javetCallbackContextSetter) + throws JavetException; /** * Delete property by key object. @@ -277,14 +217,34 @@ default boolean deleteUndefined() throws JavetException { * @param consumer the consumer * @return the key count * @throws JavetException the javet exception - * @throws E the exception + * @throws E the custom exception * @since 0.8.10 */ default int forEach( - IJavetUniConsumer consumer) throws JavetException, E { + IJavetUniConsumer consumer) + throws JavetException, E { + return forEach(consumer, DEFAULT_BATCH_SIZE); + } + + /** + * Invoke the uni-consumer for each of the keys. + * + * @param the type of key + * @param the type of exception + * @param consumer the consumer + * @param batchSize the batch size + * @return the key count + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default int forEach( + IJavetUniConsumer consumer, + int batchSize) + throws JavetException, E { Objects.requireNonNull(consumer); try (IV8ValueArray iV8ValueArray = getOwnPropertyNames()) { - return iV8ValueArray.forEach(consumer); + return iV8ValueArray.forEach(consumer, batchSize); } } @@ -296,14 +256,34 @@ default int forEach( * @param consumer the consumer * @return the key count * @throws JavetException the javet exception - * @throws E the exception + * @throws E the custom exception * @since 0.8.10 */ default int forEach( - IJavetUniIndexedConsumer consumer) throws JavetException, E { + IJavetUniIndexedConsumer consumer) + throws JavetException, E { + return forEach(consumer, DEFAULT_BATCH_SIZE); + } + + /** + * Invoke the uni-indexed-consumer for each of the keys. + * + * @param the type of key + * @param the type of exception + * @param consumer the consumer + * @param batchSize the batch size + * @return the key count + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + default int forEach( + IJavetUniIndexedConsumer consumer, + int batchSize) + throws JavetException, E { Objects.requireNonNull(consumer); try (IV8ValueArray iV8ValueArray = getOwnPropertyNames()) { - return iV8ValueArray.forEach(consumer); + return iV8ValueArray.forEach(consumer, batchSize); } } @@ -316,21 +296,33 @@ default int forEach( * @param consumer the consumer * @return the key count * @throws JavetException the javet exception - * @throws E the exception + * @throws E the custom exception * @since 0.8.9 */ default int forEach( - IJavetBiConsumer consumer) throws JavetException, E { - Objects.requireNonNull(consumer); - try (IV8ValueArray iV8ValueArray = getOwnPropertyNames()) { - return iV8ValueArray.forEach((Key key) -> { - try (Value value = get(key)) { - consumer.accept(key, value); - } - }); - } + IJavetBiConsumer consumer) + throws JavetException, E { + return forEach(consumer, DEFAULT_BATCH_SIZE); } + /** + * Invoke the bi-consumer for each of the keys. + * + * @param the type of key + * @param the type of value + * @param the type of exception + * @param consumer the consumer + * @param batchSize the batch size + * @return the key count + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 2.2.0 + */ + int forEach( + IJavetBiConsumer consumer, + int batchSize) + throws JavetException, E; + /** * Invoke the bi-indexed-consumer for each of the keys. * @@ -340,21 +332,33 @@ default int fo * @param consumer the consumer * @return the key count * @throws JavetException the javet exception - * @throws E the exception + * @throws E the custom exception * @since 0.8.10 */ default int forEach( - IJavetBiIndexedConsumer consumer) throws JavetException, E { - Objects.requireNonNull(consumer); - try (IV8ValueArray iV8ValueArray = getOwnPropertyNames()) { - return iV8ValueArray.forEach((int index, Key key) -> { - try (Value value = get(key)) { - consumer.accept(index, key, value); - } - }); - } + IJavetBiIndexedConsumer consumer) + throws JavetException, E { + return forEach(consumer, DEFAULT_BATCH_SIZE); } + /** + * Invoke the bi-indexed-consumer for each of the keys. + * + * @param the type of key + * @param the type of value + * @param the type of exception + * @param consumer the consumer + * @param batchSize the batch size + * @return the key count + * @throws JavetException the javet exception + * @throws E the custom exception + * @since 0.8.10 + */ + int forEach( + IJavetBiIndexedConsumer consumer, + int batchSize) + throws JavetException, E; + /** * Get property value by key object. *

    @@ -389,9 +393,7 @@ default BigInteger getBigInteger(Object key) throws JavetException { * @throws JavetException the javet exception * @since 0.7.0 */ - default Boolean getBoolean(Object key) throws JavetException { - return getPrimitive(key); - } + Boolean getBoolean(Object key) throws JavetException; /** * Gets property value as double by key object. @@ -401,9 +403,7 @@ default Boolean getBoolean(Object key) throws JavetException { * @throws JavetException the javet exception * @since 0.7.0 */ - default Double getDouble(Object key) throws JavetException { - return getPrimitive(key); - } + Double getDouble(Object key) throws JavetException; /** * Gets property value as float by key object. @@ -439,9 +439,7 @@ default Float getFloat(Object key) throws JavetException { * @throws JavetException the javet exception * @since 0.7.0 */ - default Integer getInteger(Object key) throws JavetException { - return getPrimitive(key); - } + Integer getInteger(Object key) throws JavetException; /** * Gets property value as long by key object. @@ -451,9 +449,7 @@ default Integer getInteger(Object key) throws JavetException { * @throws JavetException the javet exception * @since 0.7.0 */ - default Long getLong(Object key) throws JavetException { - return getPrimitive(key); - } + Long getLong(Object key) throws JavetException; /** * Gets property value as null by key object. @@ -869,9 +865,7 @@ default ZonedDateTime getPropertyZonedDateTime(Object key) throws JavetException * @throws JavetException the javet exception * @since 0.7.0 */ - default String getString(Object key) throws JavetException { - return getPrimitive(key); - } + String getString(Object key) throws JavetException; /** * Gets undefined by key object. @@ -1198,6 +1192,63 @@ default boolean isGeneratorObject() throws JavetException { */ boolean set(Object key, Object value) throws JavetException; + /** + * Set property by pairs of key object and value object. + * + * @param keysAndValues the keys and values + * @return true : set, false: not set + * @throws JavetException the javet exception + */ + boolean set(Object... keysAndValues) throws JavetException; + + /** + * Set property by key object and value boolean. + * + * @param key the key + * @param value the value + * @return true : set, false: not set + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("UnusedReturnValue") + boolean setBoolean(Object key, Boolean value) throws JavetException; + + /** + * Set property by key object and value double. + * + * @param key the key + * @param value the value + * @return true : set, false: not set + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("UnusedReturnValue") + boolean setDouble(Object key, Double value) throws JavetException; + + /** + * Set property by key object and value integer. + * + * @param key the key + * @param value the value + * @return true : set, false: not set + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("UnusedReturnValue") + boolean setInteger(Object key, Integer value) throws JavetException; + + /** + * Set property by key object and value long. + * + * @param key the key + * @param value the value + * @return true : set, false: not set + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("UnusedReturnValue") + boolean setLong(Object key, Long value) throws JavetException; + /** * Set property to null by key object. * @@ -1207,9 +1258,7 @@ default boolean isGeneratorObject() throws JavetException { * @since 0.7.0 */ @SuppressWarnings("UnusedReturnValue") - default boolean setNull(Object key) throws JavetException { - return set(key, getV8Runtime().createV8ValueNull()); - } + boolean setNull(Object key) throws JavetException; /** * Set private property by name string and value object. @@ -1292,6 +1341,18 @@ default boolean setPropertyUndefined(Object key) throws JavetException { @SuppressWarnings("UnusedReturnValue") boolean setPrototype(IV8ValueObject v8ValueObject) throws JavetException; + /** + * Set property by key object and value string. + * + * @param key the key + * @param value the value + * @return true : set, false: not set + * @throws JavetException the javet exception + * @since 2.2.0 + */ + @SuppressWarnings("UnusedReturnValue") + boolean setString(Object key, String value) throws JavetException; + /** * Set property to undefined by key object. * @@ -1301,9 +1362,7 @@ default boolean setPropertyUndefined(Object key) throws JavetException { * @since 0.7.0 */ @SuppressWarnings("UnusedReturnValue") - default boolean setUndefined(Object key) throws JavetException { - return set(key, getV8Runtime().createV8ValueUndefined()); - } + boolean setUndefined(Object key) throws JavetException; /** * To json string. @@ -1368,10 +1427,21 @@ default boolean unbindFunction(V8ValueString functionName) throws JavetException * @throws JavetException the javet exception * @since 1.0.0 */ + @SuppressWarnings("UnusedReturnValue") default boolean unbindFunction(V8ValueSymbol functionName) throws JavetException { return delete(functionName); } + /** + * Unbind property by callback context. + * + * @param javetCallbackContext the javet callback context + * @return true : the property is unbind, false: the property is not unbind + * @throws JavetException the javet exception + * @since 2.2.0 + */ + boolean unbindProperty(JavetCallbackContext javetCallbackContext) throws JavetException; + /** * Unbind property by property name string. * @@ -1381,8 +1451,7 @@ default boolean unbindFunction(V8ValueSymbol functionName) throws JavetException * @since 0.9.11 */ default boolean unbindProperty(String propertyName) throws JavetException { - Objects.requireNonNull(propertyName); - return unbindProperty(getV8Runtime().createV8ValueString(propertyName)); + return unbindProperty(getV8Runtime().createV8ValueString(Objects.requireNonNull(propertyName))); } /** diff --git a/src/main/java/com/caoccao/javet/values/reference/V8Module.java b/src/main/java/com/caoccao/javet/values/reference/V8Module.java index c9281845c..f5d4ed0fd 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8Module.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8Module.java @@ -60,7 +60,7 @@ public T evaluate(boolean resultRequired) throws JavetExcept @Override public byte[] getCachedData() throws JavetException { - return checkV8Runtime().getV8Internal().getCachedData(this); + return checkV8Runtime().getV8Internal().moduleGetCachedData(this); } @Override diff --git a/src/main/java/com/caoccao/javet/values/reference/V8Script.java b/src/main/java/com/caoccao/javet/values/reference/V8Script.java index f3da5a2e3..e158ebb3c 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8Script.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8Script.java @@ -59,7 +59,7 @@ public T execute(boolean resultRequired) throws JavetExcepti @Override public byte[] getCachedData() throws JavetException { - return checkV8Runtime().getV8Internal().getCachedData(this); + return checkV8Runtime().getV8Internal().scriptGetCachedData(this); } @Override diff --git a/src/main/java/com/caoccao/javet/values/reference/V8ValueArray.java b/src/main/java/com/caoccao/javet/values/reference/V8ValueArray.java index 389e0f206..299124f01 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8ValueArray.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8ValueArray.java @@ -22,12 +22,20 @@ import com.caoccao.javet.interfaces.IJavetUniConsumer; import com.caoccao.javet.interfaces.IJavetUniIndexedConsumer; import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.utils.JavetResourceUtils; import com.caoccao.javet.values.V8Value; import java.util.ArrayList; +import java.util.Arrays; import java.util.List; import java.util.Objects; +/** + * The type V8 value array. + * + * @since 0.7.0 + */ +@SuppressWarnings("unchecked") public class V8ValueArray extends V8ValueObject implements IV8ValueArray { protected static final String FUNCTION_KEYS = "keys"; protected static final String FUNCTION_NEXT = "next"; @@ -40,14 +48,41 @@ public class V8ValueArray extends V8ValueObject implements IV8ValueArray { super(v8Runtime, handle); } + @Override + public int batchGet(V8Value[] v8Values, int startIndex, int endIndex) throws JavetException { + return checkV8Runtime().getV8Internal().batchArrayGet(this, v8Values, startIndex, endIndex); + } + + @Override + public int forEach( + IJavetUniConsumer consumer) + throws JavetException, E { + return forEach(consumer, DEFAULT_BATCH_SIZE); + } + @Override public int forEach( - IJavetUniConsumer consumer) throws JavetException, E { + IJavetUniConsumer consumer, + int batchSize) + throws JavetException, E { Objects.requireNonNull(consumer); + batchSize = Math.max(MIN_BATCH_SIZE, batchSize); final int length = getLength(); - for (int i = 0; i < length; ++i) { - try (Value value = get(i)) { - consumer.accept(value); + if (length > 0) { + V8Value[] v8Values = new V8Value[batchSize]; + final int loopCount = (length + batchSize - 1) / batchSize; + for (int i = 0; i < loopCount; i++) { + final int startIndex = i * batchSize; + final int endIndex = i == loopCount - 1 ? length : startIndex + batchSize; + try { + int actualLength = batchGet(v8Values, startIndex, endIndex); + for (int j = 0; j < actualLength; j++) { + consumer.accept((Value) v8Values[j]); + } + } finally { + JavetResourceUtils.safeClose(v8Values); + Arrays.fill(v8Values, null); + } } } return length; @@ -55,12 +90,34 @@ public int forEach( @Override public int forEach( - IJavetUniIndexedConsumer consumer) throws JavetException, E { + IJavetUniIndexedConsumer consumer) + throws JavetException, E { + return forEach(consumer, DEFAULT_BATCH_SIZE); + } + + @Override + public int forEach( + IJavetUniIndexedConsumer consumer, + int batchSize) + throws JavetException, E { Objects.requireNonNull(consumer); + batchSize = Math.max(MIN_BATCH_SIZE, batchSize); final int length = getLength(); - for (int i = 0; i < length; ++i) { - try (Value value = get(i)) { - consumer.accept(i, value); + if (length > 0) { + V8Value[] v8Values = new V8Value[batchSize]; + final int loopCount = (length + batchSize - 1) / batchSize; + for (int i = 0; i < loopCount; i++) { + final int startIndex = i * batchSize; + final int endIndex = i == loopCount - 1 ? length : startIndex + batchSize; + try { + int actualLength = batchGet(v8Values, startIndex, endIndex); + for (int j = 0; j < actualLength; j++) { + consumer.accept(startIndex + j, (Value) v8Values[j]); + } + } finally { + JavetResourceUtils.safeClose(v8Values); + Arrays.fill(v8Values, null); + } } } return length; @@ -69,7 +126,7 @@ public int forEach( @Override @CheckReturnValue public T get(int index) throws JavetException { - return checkV8Runtime().getV8Internal().get(this, v8Runtime.createV8ValueInteger(index)); + return checkV8Runtime().getV8Internal().objectGet(this, v8Runtime.createV8ValueInteger(index)); } @Override @@ -90,7 +147,7 @@ public List getKeys() throws JavetException { @Override public int getLength() throws JavetException { - return checkV8Runtime().getV8Internal().getLength(this); + return checkV8Runtime().getV8Internal().arrayGetLength(this); } @Override @@ -105,7 +162,7 @@ public T pop() throws JavetException { } @Override - public int push(Object value) throws JavetException { - return invokeInteger(FUNCTION_PUSH, value); + public int push(Object... objects) throws JavetException { + return invokeInteger(FUNCTION_PUSH, objects); } } diff --git a/src/main/java/com/caoccao/javet/values/reference/V8ValueFunction.java b/src/main/java/com/caoccao/javet/values/reference/V8ValueFunction.java index a3d0ce041..4e27e203a 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8ValueFunction.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8ValueFunction.java @@ -79,14 +79,14 @@ protected V8ValueFunction(V8Runtime v8Runtime, long handle) throws JavetExceptio @CheckReturnValue public T callAsConstructor(Object... objects) throws JavetException { try (V8VirtualValueList virtualValueList = new V8VirtualValueList(checkV8Runtime(), null, objects)) { - return v8Runtime.getV8Internal().callAsConstructor(this, virtualValueList.get()); + return v8Runtime.getV8Internal().functionCallAsConstructor(this, virtualValueList.get()); } } @Override @CheckReturnValue public T callAsConstructor(V8Value... v8Values) throws JavetException { - return checkV8Runtime().getV8Internal().callAsConstructor(this, v8Values); + return checkV8Runtime().getV8Internal().functionCallAsConstructor(this, v8Values); } @Override @@ -94,14 +94,14 @@ public T callAsConstructor(V8Value... v8Values) throws Javet public T callExtended(IV8ValueObject receiver, boolean returnResult, Object... objects) throws JavetException { try (V8VirtualValueList virtualValueList = new V8VirtualValueList(checkV8Runtime(), null, objects)) { - return v8Runtime.getV8Internal().call(this, receiver, returnResult, virtualValueList.get()); + return v8Runtime.getV8Internal().functionCall(this, receiver, returnResult, virtualValueList.get()); } } @Override @CheckReturnValue public T callExtended(IV8ValueObject receiver, boolean returnResult, V8Value... v8Values) throws JavetException { - return checkV8Runtime().getV8Internal().call(this, receiver, returnResult, v8Values); + return checkV8Runtime().getV8Internal().functionCall(this, receiver, returnResult, v8Values); } @Override @@ -131,7 +131,7 @@ public String[] getArguments() throws JavetException { @Override public byte[] getCachedData() throws JavetException { - return checkV8Runtime().getV8Internal().getCachedData(this); + return checkV8Runtime().getV8Internal().functionGetCachedData(this); } @Override @@ -142,20 +142,20 @@ public V8Context getContext() throws JavetException { @Override @CheckReturnValue public IV8ValueArray getInternalProperties() throws JavetException { - return checkV8Runtime().getV8Internal().getInternalProperties(this); + return checkV8Runtime().getV8Internal().functionGetInternalProperties(this); } @Override public JSFunctionType getJSFunctionType() throws JavetException { if (jsFunctionType == null) { - jsFunctionType = checkV8Runtime().getV8Internal().getJSFunctionType(this); + jsFunctionType = checkV8Runtime().getV8Internal().functionGetJSFunctionType(this); } return jsFunctionType; } @Override public JSScopeType getJSScopeType() throws JavetException { - return checkV8Runtime().getV8Internal().getJSScopeType(this); + return checkV8Runtime().getV8Internal().functionGetJSScopeType(this); } @CheckReturnValue diff --git a/src/main/java/com/caoccao/javet/values/reference/V8ValueMap.java b/src/main/java/com/caoccao/javet/values/reference/V8ValueMap.java index 463fe7a44..9752f0259 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8ValueMap.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8ValueMap.java @@ -25,6 +25,8 @@ import com.caoccao.javet.interfaces.IJavetUniIndexedConsumer; import com.caoccao.javet.interop.V8Runtime; import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.virtual.V8VirtualValue; +import com.caoccao.javet.values.virtual.V8VirtualValueList; import java.util.Objects; @@ -38,6 +40,14 @@ public class V8ValueMap extends V8ValueObject implements IV8ValueMap { super(v8Runtime, handle); } + @Override + public boolean delete(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapDelete(this, virtualKey.get()); + } + } + @Override public int forEach( IJavetUniConsumer consumer) throws JavetException, E { @@ -118,21 +128,69 @@ public int for return count; } + @Override + public T get(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapGet(this, virtualKey.get()); + } + } + + @Override + public Boolean getBoolean(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapGetBoolean(this, virtualKey.get()); + } + } + + @Override + public Double getDouble(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapGetDouble(this, virtualKey.get()); + } + } + @Override @CheckReturnValue public IV8ValueIterator getEntries() throws JavetException { return invoke(FUNCTION_ENTRIES); } + @Override + public Integer getInteger(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapGetInteger(this, virtualKey.get()); + } + } + @Override @CheckReturnValue public IV8ValueIterator getKeys() throws JavetException { return invoke(FUNCTION_KEYS); } + @Override + public Long getLong(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapGetLong(this, virtualKey.get()); + } + } + @Override public int getSize() throws JavetException { - return checkV8Runtime().getV8Internal().getSize(this); + return checkV8Runtime().getV8Internal().mapGetSize(this); + } + + @Override + public String getString(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapGetString(this, virtualKey.get()); + } } @Override @@ -145,4 +203,113 @@ public V8ValueReferenceType getType() { public IV8ValueIterator getValues() throws JavetException { return invoke(FUNCTION_VALUES); } + + @Override + public boolean has(Object value) throws JavetException { + try (V8VirtualValue virtualValue = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(value))) { + return v8Runtime.getV8Internal().mapHas(this, virtualValue.get()); + } + } + + @Override + public boolean set(Object key, Object value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key)); + V8VirtualValue virtualValue = new V8VirtualValue(v8Runtime, null, value)) { + return v8Runtime.getV8Internal().mapSet(this, virtualKey.get(), virtualValue.get()); + } + } + + @Override + public boolean set(Object... keysAndValues) throws JavetException { + assert keysAndValues.length > 0 && keysAndValues.length % 2 == 0 : ERROR_THE_KEY_VALUE_PAIR_MUST_MATCH; + final int length = keysAndValues.length; + final int pairLength = keysAndValues.length >> 1; + Object[] keys = new Object[pairLength]; + Object[] values = new Object[pairLength]; + for (int i = 0; i < pairLength; i++) { + keys[i] = keysAndValues[i * 2]; + values[i] = keysAndValues[i * 2 + 1]; + } + try (V8VirtualValueList v8VirtualValueKeys = new V8VirtualValueList(checkV8Runtime(), OBJECT_CONVERTER, keys); + V8VirtualValueList v8VirtualValueValues = new V8VirtualValueList(v8Runtime, null, values)) { + V8Value[] v8ValueKeys = v8VirtualValueKeys.get(); + V8Value[] v8ValueValues = v8VirtualValueValues.get(); + V8Value[] v8Values = new V8Value[length]; + for (int i = 0; i < pairLength; i++) { + v8Values[i * 2] = v8ValueKeys[i]; + v8Values[i * 2 + 1] = v8ValueValues[i]; + } + return v8Runtime.getV8Internal().mapSet(this, v8Values); + } + } + + @Override + public boolean setBoolean(Object key, Boolean value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + if (value == null) { + return v8Runtime.getV8Internal().mapSetNull(this, virtualKey.get()); + } + return v8Runtime.getV8Internal().mapSetBoolean(this, virtualKey.get(), value); + } + } + + @Override + public boolean setDouble(Object key, Double value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + if (value == null) { + return v8Runtime.getV8Internal().mapSetNull(this, virtualKey.get()); + } + return v8Runtime.getV8Internal().mapSetDouble(this, virtualKey.get(), value); + } + } + + @Override + public boolean setInteger(Object key, Integer value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + if (value == null) { + return v8Runtime.getV8Internal().mapSetNull(this, virtualKey.get()); + } + return v8Runtime.getV8Internal().mapSetInteger(this, virtualKey.get(), value); + } + } + + @Override + public boolean setLong(Object key, Long value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + if (value == null) { + return v8Runtime.getV8Internal().mapSetNull(this, virtualKey.get()); + } + return v8Runtime.getV8Internal().mapSetLong(this, virtualKey.get(), value); + } + } + + @Override + public boolean setNull(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapSetNull(this, virtualKey.get()); + } + } + + @Override + public boolean setString(Object key, String value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapSetString(this, virtualKey.get(), value); + } + } + + @Override + public boolean setUndefined(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().mapSetUndefined(this, virtualKey.get()); + } + } } diff --git a/src/main/java/com/caoccao/javet/values/reference/V8ValueObject.java b/src/main/java/com/caoccao/javet/values/reference/V8ValueObject.java index 59a6085b4..3f208d3ea 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8ValueObject.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8ValueObject.java @@ -19,12 +19,17 @@ import com.caoccao.javet.annotations.*; import com.caoccao.javet.enums.V8ValueInternalType; import com.caoccao.javet.enums.V8ValueReferenceType; +import com.caoccao.javet.enums.V8ValueSymbolType; import com.caoccao.javet.exceptions.JavetError; import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interfaces.IJavetBiConsumer; +import com.caoccao.javet.interfaces.IJavetBiIndexedConsumer; import com.caoccao.javet.interop.V8Runtime; import com.caoccao.javet.interop.binding.BindingContext; import com.caoccao.javet.interop.binding.MethodDescriptor; +import com.caoccao.javet.interop.callback.IJavetDirectCallable; import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.utils.JavetResourceUtils; import com.caoccao.javet.utils.SimpleMap; import com.caoccao.javet.utils.ThreadSafeMap; import com.caoccao.javet.values.V8Value; @@ -48,6 +53,12 @@ public class V8ValueObject extends V8ValueReference implements IV8ValueObject { public static final String METHOD_PREFIX_GET = "get"; public static final String METHOD_PREFIX_IS = "is"; public static final String METHOD_PREFIX_SET = "set"; + /** + * The constant ERROR_THE_KEY_VALUE_PAIR_MUST_MATCH. + * + * @since 2.2.0 + */ + protected static final String ERROR_THE_KEY_VALUE_PAIR_MUST_MATCH = "The key value pair must match."; protected static final String FUNCTION_ADD = "add"; protected static final String FUNCTION_DELETE = "delete"; protected static final String FUNCTION_GET = "get"; @@ -83,128 +94,133 @@ public static ThreadSafeMap, BindingContext> getBindingContextMap() { return bindingContextMap; } + @Override + public int batchGet(V8Value[] v8ValueKeys, V8Value[] v8ValueValues, int length) throws JavetException { + return checkV8Runtime().getV8Internal().batchObjectGet(this, v8ValueKeys, v8ValueValues, length); + } + @Override public List bind(Object callbackReceiver) throws JavetException { Objects.requireNonNull(callbackReceiver); checkV8Runtime(); - BindingContext bindingContext = getBindingContext(callbackReceiver.getClass()); - Map propertyGetterMap = bindingContext.getPropertyGetterMap(); - Map propertySetterMap = bindingContext.getPropertySetterMap(); - Map functionMap = bindingContext.getFunctionMap(); - Method v8BindingEnabler = bindingContext.getV8BindingEnabler(); - Method v8RuntimeSetter = bindingContext.getV8RuntimeSetter(); - if (v8RuntimeSetter != null) { - try { - v8RuntimeSetter.invoke(callbackReceiver, getV8Runtime()); - } catch (Exception e) { - throw new JavetException( - JavetError.CallbackInjectionFailure, - SimpleMap.of(JavetError.PARAMETER_MESSAGE, e.getMessage()), - e); - } - } List javetCallbackContexts = new ArrayList<>(); - if (!propertyGetterMap.isEmpty()) { - for (Map.Entry entry : propertyGetterMap.entrySet()) { - String propertyName = entry.getKey(); - final MethodDescriptor getterMethodDescriptor = entry.getValue(); - try { - if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( - callbackReceiver, getterMethodDescriptor.getMethod().getName())) { - continue; - } - // Static method needs to be identified. - JavetCallbackContext javetCallbackContextGetter = new JavetCallbackContext( - Modifier.isStatic(getterMethodDescriptor.getMethod().getModifiers()) ? null : callbackReceiver, - getterMethodDescriptor.getMethod(), getterMethodDescriptor.isThisObjectRequired()); - javetCallbackContexts.add(javetCallbackContextGetter); - JavetCallbackContext javetCallbackContextSetter = null; - if (propertySetterMap.containsKey(propertyName)) { - MethodDescriptor setterMethodDescriptor = propertySetterMap.get(propertyName); - if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( - callbackReceiver, setterMethodDescriptor.getMethod().getName())) { - continue; - } - // Static method needs to be identified. - javetCallbackContextSetter = new JavetCallbackContext( - Modifier.isStatic(setterMethodDescriptor.getMethod().getModifiers()) ? null : callbackReceiver, - setterMethodDescriptor.getMethod(), setterMethodDescriptor.isThisObjectRequired()); - javetCallbackContexts.add(javetCallbackContextSetter); - } - switch (getterMethodDescriptor.getSymbolType()) { - case BuiltIn: - try (V8ValueBuiltInSymbol v8ValueBuiltInSymbol = v8Runtime.getGlobalObject().getBuiltInSymbol(); - V8ValueSymbol v8ValueSymbol = v8ValueBuiltInSymbol.getBuiltInSymbol(propertyName)) { - if (v8ValueSymbol == null) { - throw new JavetException( - JavetError.ConverterSymbolNotBuiltIn, - SimpleMap.of(JavetError.PARAMETER_SYMBOL, propertyName)); - } - bindProperty(v8ValueSymbol, javetCallbackContextGetter, javetCallbackContextSetter); - } + if (callbackReceiver instanceof IJavetDirectCallable) { + IJavetDirectCallable javetDirectCallable = (IJavetDirectCallable) callbackReceiver; + javetDirectCallable.setV8Runtime(v8Runtime); + JavetCallbackContext[] contexts = javetDirectCallable.getCallbackContexts(); + if (contexts != null && contexts.length > 0) { + Map getterMap = new HashMap<>(); + Map setterMap = new HashMap<>(); + for (JavetCallbackContext javetCallbackContext : contexts) { + switch (javetCallbackContext.getCallbackType()) { + case DirectCallGetterAndNoThis: + case DirectCallGetterAndThis: + getterMap.put(javetCallbackContext.getName(), javetCallbackContext); break; - case Custom: - try (V8ValueSymbol v8ValueSymbol = v8Runtime.createV8ValueSymbol(propertyName, true)) { - bindProperty(v8ValueSymbol, javetCallbackContextGetter, javetCallbackContextSetter); - } + case DirectCallSetterAndNoThis: + case DirectCallSetterAndThis: + setterMap.put(javetCallbackContext.getName(), javetCallbackContext); break; default: - bindProperty(propertyName, javetCallbackContextGetter, javetCallbackContextSetter); + javetCallbackContexts.add(javetCallbackContext); + bindFunction(javetCallbackContext); break; } + } + for (JavetCallbackContext javetCallbackContextGetter : getterMap.values()) { + JavetCallbackContext javetCallbackContextSetter = setterMap.get(javetCallbackContextGetter.getName()); + javetCallbackContexts.add(javetCallbackContextGetter); + if (javetCallbackContextSetter != null) { + javetCallbackContexts.add(javetCallbackContextSetter); + } + bindProperty(javetCallbackContextGetter, javetCallbackContextSetter); + } + } + } else { + BindingContext bindingContext = getBindingContext(callbackReceiver.getClass()); + Map propertyGetterMap = bindingContext.getPropertyGetterMap(); + Map propertySetterMap = bindingContext.getPropertySetterMap(); + Map functionMap = bindingContext.getFunctionMap(); + Method v8BindingEnabler = bindingContext.getV8BindingEnabler(); + Method v8RuntimeSetter = bindingContext.getV8RuntimeSetter(); + if (v8RuntimeSetter != null) { + try { + v8RuntimeSetter.invoke(callbackReceiver, getV8Runtime()); } catch (Exception e) { throw new JavetException( - JavetError.CallbackRegistrationFailure, - SimpleMap.of( - JavetError.PARAMETER_METHOD_NAME, getterMethodDescriptor.getMethod().getName(), - JavetError.PARAMETER_MESSAGE, e.getMessage()), + JavetError.CallbackInjectionFailure, + SimpleMap.of(JavetError.PARAMETER_MESSAGE, e.getMessage()), e); } } - } - if (!functionMap.isEmpty()) { - for (Map.Entry entry : functionMap.entrySet()) { - String functionName = entry.getKey(); - final MethodDescriptor functionMethodDescriptor = entry.getValue(); - try { - if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( - callbackReceiver, functionMethodDescriptor.getMethod().getName())) { - continue; - } - // Static method needs to be identified. - JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - Modifier.isStatic(functionMethodDescriptor.getMethod().getModifiers()) ? - null : callbackReceiver, - functionMethodDescriptor.getMethod(), functionMethodDescriptor.isThisObjectRequired()); - switch (functionMethodDescriptor.getSymbolType()) { - case BuiltIn: - try (V8ValueBuiltInSymbol v8ValueBuiltInSymbol = v8Runtime.getGlobalObject().getBuiltInSymbol(); - V8ValueSymbol v8ValueSymbol = v8ValueBuiltInSymbol.getBuiltInSymbol(functionName)) { - if (v8ValueSymbol == null) { - throw new JavetException( - JavetError.ConverterSymbolNotBuiltIn, - SimpleMap.of(JavetError.PARAMETER_SYMBOL, functionName)); - } - bindFunction(v8ValueSymbol, javetCallbackContext); - } - break; - case Custom: - try (V8ValueSymbol v8ValueSymbol = v8Runtime.createV8ValueSymbol(functionName, true)) { - bindFunction(v8ValueSymbol, javetCallbackContext); + if (!propertyGetterMap.isEmpty()) { + for (Map.Entry entry : propertyGetterMap.entrySet()) { + String propertyName = entry.getKey(); + final MethodDescriptor getterMethodDescriptor = entry.getValue(); + try { + if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( + callbackReceiver, getterMethodDescriptor.getMethod().getName())) { + continue; + } + // Static method needs to be identified. + JavetCallbackContext javetCallbackContextGetter = new JavetCallbackContext( + propertyName, + getterMethodDescriptor.getSymbolType(), + Modifier.isStatic(getterMethodDescriptor.getMethod().getModifiers()) ? null : callbackReceiver, + getterMethodDescriptor.getMethod(), getterMethodDescriptor.isThisObjectRequired()); + javetCallbackContexts.add(javetCallbackContextGetter); + JavetCallbackContext javetCallbackContextSetter = null; + if (propertySetterMap.containsKey(propertyName)) { + MethodDescriptor setterMethodDescriptor = propertySetterMap.get(propertyName); + if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( + callbackReceiver, setterMethodDescriptor.getMethod().getName())) { + continue; } - break; - default: - bindFunction(functionName, javetCallbackContext); - break; + // Static method needs to be identified. + javetCallbackContextSetter = new JavetCallbackContext( + propertyName, + setterMethodDescriptor.getSymbolType(), + Modifier.isStatic(setterMethodDescriptor.getMethod().getModifiers()) ? null : callbackReceiver, + setterMethodDescriptor.getMethod(), setterMethodDescriptor.isThisObjectRequired()); + javetCallbackContexts.add(javetCallbackContextSetter); + } + bindProperty(javetCallbackContextGetter, javetCallbackContextSetter); + } catch (Exception e) { + throw new JavetException( + JavetError.CallbackRegistrationFailure, + SimpleMap.of( + JavetError.PARAMETER_METHOD_NAME, getterMethodDescriptor.getMethod().getName(), + JavetError.PARAMETER_MESSAGE, e.getMessage()), + e); + } + } + } + if (!functionMap.isEmpty()) { + for (Map.Entry entry : functionMap.entrySet()) { + String functionName = entry.getKey(); + final MethodDescriptor functionMethodDescriptor = entry.getValue(); + try { + if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( + callbackReceiver, functionMethodDescriptor.getMethod().getName())) { + continue; + } + // Static method needs to be identified. + JavetCallbackContext javetCallbackContext = new JavetCallbackContext( + functionName, + functionMethodDescriptor.getSymbolType(), + Modifier.isStatic(functionMethodDescriptor.getMethod().getModifiers()) ? + null : callbackReceiver, + functionMethodDescriptor.getMethod(), functionMethodDescriptor.isThisObjectRequired()); + javetCallbackContexts.add(javetCallbackContext); + bindFunction(javetCallbackContext); + } catch (Exception e) { + throw new JavetException( + JavetError.CallbackRegistrationFailure, + SimpleMap.of( + JavetError.PARAMETER_METHOD_NAME, functionMethodDescriptor.getMethod().getName(), + JavetError.PARAMETER_MESSAGE, e.getMessage()), + e); } - javetCallbackContexts.add(javetCallbackContext); - } catch (Exception e) { - throw new JavetException( - JavetError.CallbackRegistrationFailure, - SimpleMap.of( - JavetError.PARAMETER_METHOD_NAME, functionMethodDescriptor.getMethod().getName(), - JavetError.PARAMETER_MESSAGE, e.getMessage()), - e); } } } @@ -212,63 +228,155 @@ public List bind(Object callbackReceiver) throws JavetExce } @Override - public boolean bindFunction(String functionName, JavetCallbackContext javetCallbackContext) throws JavetException { - Objects.requireNonNull(functionName); - try (V8ValueFunction v8ValueFunction = - checkV8Runtime().createV8ValueFunction(Objects.requireNonNull(javetCallbackContext))) { - return set(functionName, v8ValueFunction); - } - } - - @Override - public boolean bindFunction(V8ValueSymbol functionName, JavetCallbackContext javetCallbackContext) throws JavetException { - Objects.requireNonNull(functionName); - try (V8ValueFunction v8ValueFunction = - checkV8Runtime().createV8ValueFunction(Objects.requireNonNull(javetCallbackContext))) { - return set(functionName, v8ValueFunction); + public boolean bindFunction(JavetCallbackContext javetCallbackContext) throws JavetException { + String functionName = Objects.requireNonNull(javetCallbackContext).getName(); + switch (javetCallbackContext.getSymbolType()) { + case BuiltIn: + try (V8ValueBuiltInSymbol v8ValueBuiltInSymbol = v8Runtime.getGlobalObject().getBuiltInSymbol(); + V8ValueSymbol v8ValueSymbol = v8ValueBuiltInSymbol.getBuiltInSymbol(functionName)) { + if (v8ValueSymbol == null) { + throw new JavetException( + JavetError.ConverterSymbolNotBuiltIn, + SimpleMap.of(JavetError.PARAMETER_SYMBOL, functionName)); + } + try (V8ValueFunction v8ValueFunction = + checkV8Runtime().createV8ValueFunction(javetCallbackContext)) { + return set(v8ValueSymbol, v8ValueFunction); + } + } + case Custom: + try (V8ValueSymbol v8ValueSymbol = v8Runtime.createV8ValueSymbol(functionName, true); + V8ValueFunction v8ValueFunction = checkV8Runtime().createV8ValueFunction(javetCallbackContext)) { + return set(v8ValueSymbol, v8ValueFunction); + } + default: + try (V8ValueFunction v8ValueFunction = checkV8Runtime().createV8ValueFunction(javetCallbackContext)) { + return set(functionName, v8ValueFunction); + } } } @Override public boolean bindProperty( - V8ValueString propertyName, JavetCallbackContext javetCallbackContextGetter, - JavetCallbackContext javetCallbackContextSetter) throws JavetException { - return checkV8Runtime().getV8Internal().setAccessor( - this, Objects.requireNonNull(propertyName), - Objects.requireNonNull(javetCallbackContextGetter), javetCallbackContextSetter); - } - - @Override - public boolean bindProperty( - V8ValueSymbol propertyName, - JavetCallbackContext javetCallbackContextGetter, - JavetCallbackContext javetCallbackContextSetter) throws JavetException { - return checkV8Runtime().getV8Internal().setAccessor( - this, Objects.requireNonNull(propertyName), - Objects.requireNonNull(javetCallbackContextGetter), javetCallbackContextSetter); + JavetCallbackContext javetCallbackContextSetter) + throws JavetException { + String propertyName = Objects.requireNonNull(javetCallbackContextGetter).getName(); + switch (javetCallbackContextGetter.getSymbolType()) { + case BuiltIn: + try (V8ValueBuiltInSymbol v8ValueBuiltInSymbol = v8Runtime.getGlobalObject().getBuiltInSymbol(); + V8ValueSymbol v8ValueSymbol = v8ValueBuiltInSymbol.getBuiltInSymbol(propertyName)) { + if (v8ValueSymbol == null) { + throw new JavetException( + JavetError.ConverterSymbolNotBuiltIn, + SimpleMap.of(JavetError.PARAMETER_SYMBOL, propertyName)); + } + return checkV8Runtime().getV8Internal().objectSetAccessor( + this, v8ValueSymbol, javetCallbackContextGetter, javetCallbackContextSetter); + } + case Custom: + try (V8ValueSymbol v8ValueSymbol = v8Runtime.createV8ValueSymbol(propertyName, true)) { + return checkV8Runtime().getV8Internal().objectSetAccessor( + this, v8ValueSymbol, javetCallbackContextGetter, javetCallbackContextSetter); + } + default: + try (V8ValueString v8ValueString = v8Runtime.createV8ValueString(propertyName)) { + return checkV8Runtime().getV8Internal().objectSetAccessor( + this, v8ValueString, javetCallbackContextGetter, javetCallbackContextSetter); + } + } } @Override public boolean delete(Object key) throws JavetException { try (V8VirtualValue virtualKey = new V8VirtualValue( checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { - return v8Runtime.getV8Internal().delete(this, virtualKey.get()); + return v8Runtime.getV8Internal().objectDelete(this, virtualKey.get()); } } @Override public boolean deletePrivateProperty(String propertyName) throws JavetException { - return checkV8Runtime().getV8Internal().deletePrivateProperty( + return checkV8Runtime().getV8Internal().objectDeletePrivateProperty( this, Objects.requireNonNull(propertyName)); } + @Override + public int forEach( + IJavetBiConsumer consumer, + int batchSize) + throws JavetException, E { + Objects.requireNonNull(consumer); + try (IV8ValueArray iV8ValueArray = getOwnPropertyNames()) { + batchSize = Math.max(MIN_BATCH_SIZE, batchSize); + final int length = iV8ValueArray.getLength(); + if (length > 0) { + V8Value[] v8ValueKeys = new V8Value[batchSize]; + V8Value[] v8ValueValues = new V8Value[batchSize]; + final int loopCount = (length + batchSize - 1) / batchSize; + for (int i = 0; i < loopCount; i++) { + final int startIndex = i * batchSize; + final int endIndex = i == loopCount - 1 ? length : startIndex + batchSize; + try { + int actualLength = iV8ValueArray.batchGet(v8ValueKeys, startIndex, endIndex); + if (actualLength > 0) { + batchGet(v8ValueKeys, v8ValueValues, actualLength); + for (int j = 0; j < actualLength; j++) { + consumer.accept((Key) v8ValueKeys[j], (Value) v8ValueValues[j]); + } + } + } finally { + JavetResourceUtils.safeClose(v8ValueKeys); + JavetResourceUtils.safeClose(v8ValueValues); + Arrays.fill(v8ValueKeys, null); + Arrays.fill(v8ValueValues, null); + } + } + } + return length; + } + } + + @Override + public int forEach( + IJavetBiIndexedConsumer consumer, + int batchSize) + throws JavetException, E { + Objects.requireNonNull(consumer); + try (IV8ValueArray iV8ValueArray = getOwnPropertyNames()) { + batchSize = Math.max(MIN_BATCH_SIZE, batchSize); + final int length = iV8ValueArray.getLength(); + if (length > 0) { + V8Value[] v8ValueKeys = new V8Value[batchSize]; + V8Value[] v8ValueValues = new V8Value[batchSize]; + final int loopCount = (length + batchSize - 1) / batchSize; + for (int i = 0; i < loopCount; i++) { + final int startIndex = i * batchSize; + final int endIndex = i == loopCount - 1 ? length : startIndex + batchSize; + try { + int actualLength = iV8ValueArray.batchGet(v8ValueKeys, startIndex, endIndex); + batchGet(v8ValueKeys, v8ValueValues, actualLength); + for (int j = 0; j < actualLength; j++) { + consumer.accept(startIndex + j, (Key) v8ValueKeys[j], (Value) v8ValueValues[j]); + } + } finally { + JavetResourceUtils.safeClose(v8ValueKeys); + JavetResourceUtils.safeClose(v8ValueValues); + Arrays.fill(v8ValueKeys, null); + Arrays.fill(v8ValueValues, null); + } + } + } + return length; + } + } + @Override @CheckReturnValue public T get(Object key) throws JavetException { try (V8VirtualValue virtualKey = new V8VirtualValue( checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { - return v8Runtime.getV8Internal().get(this, virtualKey.get()); + return v8Runtime.getV8Internal().objectGet(this, virtualKey.get()); } } @@ -383,20 +491,52 @@ BindingContext getBindingContext(Class callbackReceiverClass) throws JavetExc return bindingContext; } + @Override + public Boolean getBoolean(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().objectGetBoolean(this, virtualKey.get()); + } + } + + @Override + public Double getDouble(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().objectGetDouble(this, virtualKey.get()); + } + } + @Override public int getIdentityHash() throws JavetException { - return checkV8Runtime().getV8Internal().getIdentityHash(this); + return checkV8Runtime().getV8Internal().objectGetIdentityHash(this); + } + + @Override + public Integer getInteger(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().objectGetInteger(this, virtualKey.get()); + } + } + + @Override + public Long getLong(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().objectGetLong(this, virtualKey.get()); + } } @Override @CheckReturnValue public IV8ValueArray getOwnPropertyNames() throws JavetException { - return checkV8Runtime().getV8Internal().getOwnPropertyNames(this); + return checkV8Runtime().getV8Internal().objectGetOwnPropertyNames(this); } @Override public T getPrivateProperty(String propertyName) throws JavetException { - return checkV8Runtime().getV8Internal().getPrivateProperty( + return checkV8Runtime().getV8Internal().objectGetPrivateProperty( this, Objects.requireNonNull(propertyName)); } @@ -405,14 +545,14 @@ public T getPrivateProperty(String propertyName) throws Jave public T getProperty(Object key) throws JavetException { try (V8VirtualValue virtualKey = new V8VirtualValue( checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { - return v8Runtime.getV8Internal().getProperty(this, virtualKey.get()); + return v8Runtime.getV8Internal().objectGetProperty(this, virtualKey.get()); } } @Override @CheckReturnValue public IV8ValueArray getPropertyNames() throws JavetException { - return checkV8Runtime().getV8Internal().getPropertyNames(this); + return checkV8Runtime().getV8Internal().objectGetPropertyNames(this); } @Override @@ -420,6 +560,14 @@ public T getPrototype() throws JavetException { return (T) get(PROPERTY_PROTOTYPE); } + @Override + public String getString(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().objectGetString(this, virtualKey.get()); + } + } + @Override public V8ValueReferenceType getType() { return V8ValueReferenceType.Object; @@ -429,7 +577,7 @@ public V8ValueReferenceType getType() { public boolean has(Object value) throws JavetException { try (V8VirtualValue virtualValue = new V8VirtualValue( checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(value))) { - return v8Runtime.getV8Internal().has(this, virtualValue.get()); + return v8Runtime.getV8Internal().objectHas(this, virtualValue.get()); } } @@ -442,13 +590,13 @@ public boolean hasInternalType(V8ValueInternalType internalType) throws JavetExc public boolean hasOwnProperty(Object key) throws JavetException { try (V8VirtualValue virtualKey = new V8VirtualValue( checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { - return v8Runtime.getV8Internal().hasOwnProperty(this, virtualKey.get()); + return v8Runtime.getV8Internal().objectHasOwnProperty(this, virtualKey.get()); } } @Override public boolean hasPrivateProperty(String propertyName) throws JavetException { - return checkV8Runtime().getV8Internal().hasPrivateProperty( + return checkV8Runtime().getV8Internal().objectHasPrivateProperty( this, Objects.requireNonNull(propertyName)); } @@ -458,7 +606,7 @@ public T invokeExtended(String functionName, boolean returnR throws JavetException { Objects.requireNonNull(functionName); try (V8VirtualValueList virtualValueList = new V8VirtualValueList(checkV8Runtime(), null, objects)) { - return v8Runtime.getV8Internal().invoke( + return v8Runtime.getV8Internal().objectInvoke( this, functionName, returnResult, virtualValueList.get()); } } @@ -468,7 +616,7 @@ public T invokeExtended(String functionName, boolean returnR public T invokeExtended(String functionName, boolean returnResult, V8Value... v8Values) throws JavetException { Objects.requireNonNull(functionName); - return checkV8Runtime().getV8Internal().invoke(this, functionName, returnResult, v8Values); + return checkV8Runtime().getV8Internal().objectInvoke(this, functionName, returnResult, v8Values); } @Override @@ -491,7 +639,83 @@ public boolean set(Object key, Object value) throws JavetException { try (V8VirtualValue virtualKey = new V8VirtualValue( checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key)); V8VirtualValue virtualValue = new V8VirtualValue(v8Runtime, null, value)) { - return v8Runtime.getV8Internal().set(this, virtualKey.get(), virtualValue.get()); + return v8Runtime.getV8Internal().objectSet(this, virtualKey.get(), virtualValue.get()); + } + } + + @Override + public boolean set(Object... keysAndValues) throws JavetException { + assert keysAndValues.length > 0 && keysAndValues.length % 2 == 0 : ERROR_THE_KEY_VALUE_PAIR_MUST_MATCH; + final int length = keysAndValues.length; + final int pairLength = keysAndValues.length >> 1; + Object[] keys = new Object[pairLength]; + Object[] values = new Object[pairLength]; + for (int i = 0; i < pairLength; i++) { + keys[i] = keysAndValues[i * 2]; + values[i] = keysAndValues[i * 2 + 1]; + } + try (V8VirtualValueList v8VirtualValueKeys = new V8VirtualValueList(checkV8Runtime(), OBJECT_CONVERTER, keys); + V8VirtualValueList v8VirtualValueValues = new V8VirtualValueList(v8Runtime, null, values)) { + V8Value[] v8ValueKeys = v8VirtualValueKeys.get(); + V8Value[] v8ValueValues = v8VirtualValueValues.get(); + V8Value[] v8Values = new V8Value[length]; + for (int i = 0; i < pairLength; i++) { + v8Values[i * 2] = v8ValueKeys[i]; + v8Values[i * 2 + 1] = v8ValueValues[i]; + } + return v8Runtime.getV8Internal().objectSet(this, v8Values); + } + } + + @Override + public boolean setBoolean(Object key, Boolean value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + if (value == null) { + return v8Runtime.getV8Internal().objectSetNull(this, virtualKey.get()); + } + return v8Runtime.getV8Internal().objectSetBoolean(this, virtualKey.get(), value); + } + } + + @Override + public boolean setDouble(Object key, Double value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + if (value == null) { + return v8Runtime.getV8Internal().objectSetNull(this, virtualKey.get()); + } + return v8Runtime.getV8Internal().objectSetDouble(this, virtualKey.get(), value); + } + } + + @Override + public boolean setInteger(Object key, Integer value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + if (value == null) { + return v8Runtime.getV8Internal().objectSetNull(this, virtualKey.get()); + } + return v8Runtime.getV8Internal().objectSetInteger(this, virtualKey.get(), value); + } + } + + @Override + public boolean setLong(Object key, Long value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + if (value == null) { + return v8Runtime.getV8Internal().objectSetNull(this, virtualKey.get()); + } + return v8Runtime.getV8Internal().objectSetLong(this, virtualKey.get(), value); + } + } + + @Override + public boolean setNull(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().objectSetNull(this, virtualKey.get()); } } @@ -499,7 +723,7 @@ public boolean set(Object key, Object value) throws JavetException { public boolean setPrivateProperty(String propertyName, Object propertyValue) throws JavetException { Objects.requireNonNull(propertyName); try (V8VirtualValue virtualValue = new V8VirtualValue(checkV8Runtime(), null, propertyValue)) { - return v8Runtime.getV8Internal().setPrivateProperty(this, propertyName, virtualValue.get()); + return v8Runtime.getV8Internal().objectSetPrivateProperty(this, propertyName, virtualValue.get()); } } @@ -508,7 +732,7 @@ public boolean setProperty(Object key, Object value) throws JavetException { try (V8VirtualValue virtualKey = new V8VirtualValue( checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key)); V8VirtualValue virtualValue = new V8VirtualValue(v8Runtime, null, value)) { - return v8Runtime.getV8Internal().setProperty(this, virtualKey.get(), virtualValue.get()); + return v8Runtime.getV8Internal().objectSetProperty(this, virtualKey.get(), virtualValue.get()); } } @@ -517,6 +741,22 @@ public boolean setPrototype(IV8ValueObject v8ValueObject) throws JavetException return set(PROPERTY_PROTOTYPE, Objects.requireNonNull(v8ValueObject)); } + @Override + public boolean setString(Object key, String value) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().objectSetString(this, virtualKey.get(), value); + } + } + + @Override + public boolean setUndefined(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().objectSetUndefined(this, virtualKey.get()); + } + } + @Override public boolean strictEquals(V8Value v8Value) throws JavetException { if (!(v8Value instanceof V8ValueObject)) { @@ -546,7 +786,7 @@ public String toJsonString() { @Override public String toProtoString() { try { - return checkV8Runtime().getV8Internal().toProtoString(this); + return checkV8Runtime().getV8Internal().objectToProtoString(this); } catch (JavetException e) { return e.getMessage(); } @@ -556,112 +796,147 @@ public String toProtoString() { public int unbind(Object callbackReceiver) throws JavetException { Objects.requireNonNull(callbackReceiver); checkV8Runtime(); - BindingContext bindingContext = getBindingContext(callbackReceiver.getClass()); - Map propertyGetterMap = bindingContext.getPropertyGetterMap(); - Map propertySetterMap = bindingContext.getPropertySetterMap(); - Map functionMap = bindingContext.getFunctionMap(); - Method v8BindingEnabler = bindingContext.getV8BindingEnabler(); int unbindCount = 0; - if (!propertyGetterMap.isEmpty()) { - for (Map.Entry entry : propertyGetterMap.entrySet()) { - String propertyName = entry.getKey(); - final MethodDescriptor getterMethodDescriptor = entry.getValue(); - try { - if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( - callbackReceiver, getterMethodDescriptor.getMethod().getName())) { - continue; + if (callbackReceiver instanceof IJavetDirectCallable) { + IJavetDirectCallable javetDirectCallable = (IJavetDirectCallable) callbackReceiver; + javetDirectCallable.setV8Runtime(v8Runtime); + for (JavetCallbackContext javetCallbackContext : + Objects.requireNonNull(javetDirectCallable.getCallbackContexts())) { + boolean success; + switch (javetCallbackContext.getCallbackType()) { + case DirectCallSetterAndNoThis: + case DirectCallSetterAndThis: + // Generic getter or setter is ignored and there's no need to unbind setter. + success = false; + break; + case DirectCallGetterAndNoThis: + case DirectCallGetterAndThis: + success = unbindProperty(javetCallbackContext); + break; + default: + success = unbindFunction(javetCallbackContext.getName()); + break; + } + if (success) { + ++unbindCount; + } + } + } else { + BindingContext bindingContext = getBindingContext(callbackReceiver.getClass()); + Map propertyGetterMap = bindingContext.getPropertyGetterMap(); + Map propertySetterMap = bindingContext.getPropertySetterMap(); + Map functionMap = bindingContext.getFunctionMap(); + Method v8BindingEnabler = bindingContext.getV8BindingEnabler(); + if (!propertyGetterMap.isEmpty()) { + for (Map.Entry entry : propertyGetterMap.entrySet()) { + String propertyName = entry.getKey(); + final MethodDescriptor getterMethodDescriptor = entry.getValue(); + try { + if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( + callbackReceiver, getterMethodDescriptor.getMethod().getName())) { + continue; + } + if (unbindProperty(propertyName, getterMethodDescriptor.getSymbolType())) { + ++unbindCount; + } + } catch (Exception e) { + throw new JavetException( + JavetError.CallbackUnregistrationFailure, + SimpleMap.of( + JavetError.PARAMETER_METHOD_NAME, getterMethodDescriptor.getMethod().getName(), + JavetError.PARAMETER_MESSAGE, e.getMessage()), + e); } - switch (getterMethodDescriptor.getSymbolType()) { - case BuiltIn: - try (V8ValueBuiltInSymbol v8ValueBuiltInSymbol = v8Runtime.getGlobalObject().getBuiltInSymbol(); - V8ValueSymbol v8ValueSymbol = v8ValueBuiltInSymbol.getBuiltInSymbol(propertyName)) { - if (v8ValueSymbol == null) { - throw new JavetException( - JavetError.ConverterSymbolNotBuiltIn, - SimpleMap.of(JavetError.PARAMETER_SYMBOL, propertyName)); - } - if (unbindProperty(v8ValueSymbol)) { - ++unbindCount; - } - } - break; - case Custom: - try (V8ValueSymbol v8ValueSymbol = v8Runtime.createV8ValueSymbol(propertyName, true)) { - if (unbindProperty(v8ValueSymbol)) { - ++unbindCount; - } - } - break; - default: - if (unbindProperty(propertyName)) { - ++unbindCount; - } - break; + } + } + if (!functionMap.isEmpty()) { + for (Map.Entry entry : functionMap.entrySet()) { + String functionName = entry.getKey(); + final MethodDescriptor functionMethodDescriptor = entry.getValue(); + try { + if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( + callbackReceiver, functionMethodDescriptor.getMethod().getName())) { + continue; + } + if (unbindFunction(functionName, functionMethodDescriptor.getSymbolType())) { + ++unbindCount; + } + } catch (Exception e) { + throw new JavetException( + JavetError.CallbackUnregistrationFailure, + SimpleMap.of( + JavetError.PARAMETER_METHOD_NAME, functionMethodDescriptor.getMethod().getName(), + JavetError.PARAMETER_MESSAGE, e.getMessage()), + e); } - } catch (Exception e) { - throw new JavetException( - JavetError.CallbackUnregistrationFailure, - SimpleMap.of( - JavetError.PARAMETER_METHOD_NAME, getterMethodDescriptor.getMethod().getName(), - JavetError.PARAMETER_MESSAGE, e.getMessage()), - e); } } } - if (!functionMap.isEmpty()) { - for (Map.Entry entry : functionMap.entrySet()) { - String functionName = entry.getKey(); - final MethodDescriptor functionMethodDescriptor = entry.getValue(); - try { - if (v8BindingEnabler != null && !(boolean) v8BindingEnabler.invoke( - callbackReceiver, functionMethodDescriptor.getMethod().getName())) { - continue; + return unbindCount; + } + + protected boolean unbindFunction(String functionName, V8ValueSymbolType symbolType) throws JavetException { + Objects.requireNonNull(functionName); + switch (Objects.requireNonNull(symbolType)) { + case BuiltIn: + try (V8ValueBuiltInSymbol v8ValueBuiltInSymbol = v8Runtime.getGlobalObject().getBuiltInSymbol(); + V8ValueSymbol v8ValueSymbol = v8ValueBuiltInSymbol.getBuiltInSymbol(functionName)) { + if (v8ValueSymbol == null) { + throw new JavetException( + JavetError.ConverterSymbolNotBuiltIn, + SimpleMap.of(JavetError.PARAMETER_SYMBOL, functionName)); } - switch (functionMethodDescriptor.getSymbolType()) { - case BuiltIn: - try (V8ValueBuiltInSymbol v8ValueBuiltInSymbol = v8Runtime.getGlobalObject().getBuiltInSymbol(); - V8ValueSymbol v8ValueSymbol = v8ValueBuiltInSymbol.getBuiltInSymbol(functionName)) { - if (v8ValueSymbol == null) { - throw new JavetException( - JavetError.ConverterSymbolNotBuiltIn, - SimpleMap.of(JavetError.PARAMETER_SYMBOL, functionName)); - } - unbindFunction(v8ValueSymbol); - } - break; - case Custom: - try (V8ValueSymbol v8ValueSymbol = v8Runtime.createV8ValueSymbol(functionName, true)) { - unbindFunction(v8ValueSymbol); - } - break; - default: - if (unbindFunction(functionName)) { - ++unbindCount; - } - break; + return delete(v8ValueSymbol); + } + case Custom: + try (V8ValueSymbol v8ValueSymbol = v8Runtime.createV8ValueSymbol(functionName, true)) { + return delete(v8ValueSymbol); + } + default: + return delete(functionName); + } + } + + @Override + public boolean unbindProperty(JavetCallbackContext javetCallbackContext) throws JavetException { + return unbindProperty( + Objects.requireNonNull(javetCallbackContext).getName(), + javetCallbackContext.getSymbolType()); + } + + protected boolean unbindProperty(String propertyName, V8ValueSymbolType symbolType) throws JavetException { + Objects.requireNonNull(propertyName); + switch (Objects.requireNonNull(symbolType)) { + case BuiltIn: + try (V8ValueBuiltInSymbol v8ValueBuiltInSymbol = v8Runtime.getGlobalObject().getBuiltInSymbol(); + V8ValueSymbol v8ValueSymbol = v8ValueBuiltInSymbol.getBuiltInSymbol(propertyName)) { + if (v8ValueSymbol == null) { + throw new JavetException( + JavetError.ConverterSymbolNotBuiltIn, + SimpleMap.of(JavetError.PARAMETER_SYMBOL, propertyName)); } - } catch (Exception e) { - throw new JavetException( - JavetError.CallbackUnregistrationFailure, - SimpleMap.of( - JavetError.PARAMETER_METHOD_NAME, functionMethodDescriptor.getMethod().getName(), - JavetError.PARAMETER_MESSAGE, e.getMessage()), - e); + return unbindProperty(v8ValueSymbol); + } + case Custom: + try (V8ValueSymbol v8ValueSymbol = v8Runtime.createV8ValueSymbol(propertyName, true)) { + return unbindProperty(v8ValueSymbol); + } + default: + try (V8ValueString v8ValueString = v8Runtime.createV8ValueString(propertyName)) { + return unbindProperty(v8ValueString); } - } } - return unbindCount; } @Override public boolean unbindProperty(V8ValueString propertyName) throws JavetException { - return checkV8Runtime().getV8Internal().setAccessor( + return checkV8Runtime().getV8Internal().objectSetAccessor( this, Objects.requireNonNull(propertyName), null, null); } @Override public boolean unbindProperty(V8ValueSymbol propertyName) throws JavetException { - return checkV8Runtime().getV8Internal().setAccessor( + return checkV8Runtime().getV8Internal().objectSetAccessor( this, Objects.requireNonNull(propertyName), null, null); } } diff --git a/src/main/java/com/caoccao/javet/values/reference/V8ValuePromise.java b/src/main/java/com/caoccao/javet/values/reference/V8ValuePromise.java index 15114a2e9..a50c8b705 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8ValuePromise.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8ValuePromise.java @@ -82,11 +82,17 @@ public boolean register(IListener listener) throws JavetException { checkV8Runtime(); try { JavetCallbackContext contextOnCatch = new JavetCallbackContext( - listener, listener.getClass().getMethod(IListener.ON_CATCH, V8Value.class)); + IListener.ON_CATCH, + listener, + listener.getClass().getMethod(IListener.ON_CATCH, V8Value.class)); JavetCallbackContext contextOnFulfilled = new JavetCallbackContext( - listener, listener.getClass().getMethod(IListener.ON_FULFILLED, V8Value.class)); + IListener.ON_FULFILLED, + listener, + listener.getClass().getMethod(IListener.ON_FULFILLED, V8Value.class)); JavetCallbackContext contextOnRejected = new JavetCallbackContext( - listener, listener.getClass().getMethod(IListener.ON_REJECTED, V8Value.class)); + IListener.ON_REJECTED, + listener, + listener.getClass().getMethod(IListener.ON_REJECTED, V8Value.class)); try (V8ValueFunction functionOnCatch = v8Runtime.createV8ValueFunction(contextOnCatch); V8ValueFunction functionOnFulfilled = v8Runtime.createV8ValueFunction(contextOnFulfilled); V8ValueFunction functionOnRejected = v8Runtime.createV8ValueFunction(contextOnRejected); diff --git a/src/main/java/com/caoccao/javet/values/reference/V8ValueSet.java b/src/main/java/com/caoccao/javet/values/reference/V8ValueSet.java index 4287aea65..91e4eb3d4 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8ValueSet.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8ValueSet.java @@ -39,7 +39,15 @@ public class V8ValueSet extends V8ValueObject implements IV8ValueSet { @Override public void add(Object key) throws JavetException { try (V8VirtualValue virtualValue = new V8VirtualValue(checkV8Runtime(), null, key)) { - v8Runtime.getV8Internal().add(this, virtualValue.get()); + v8Runtime.getV8Internal().setAdd(this, virtualValue.get()); + } + } + + @Override + public boolean delete(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().setDelete(this, virtualKey.get()); } } @@ -95,7 +103,7 @@ public IV8ValueIterator getKeys() throws JavetException { @Override public int getSize() throws JavetException { - return checkV8Runtime().getV8Internal().getSize(this); + return checkV8Runtime().getV8Internal().setGetSize(this); } @Override @@ -103,4 +111,12 @@ public V8ValueReferenceType getType() { return V8ValueReferenceType.Set; } + @Override + public boolean has(Object value) throws JavetException { + try (V8VirtualValue virtualValue = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(value))) { + return v8Runtime.getV8Internal().setHas(this, virtualValue.get()); + } + } + } diff --git a/src/main/java/com/caoccao/javet/values/reference/V8ValueTypedArray.java b/src/main/java/com/caoccao/javet/values/reference/V8ValueTypedArray.java index fafc3a706..45a5e7512 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8ValueTypedArray.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8ValueTypedArray.java @@ -20,6 +20,8 @@ import com.caoccao.javet.enums.V8ValueReferenceType; import com.caoccao.javet.exceptions.JavetException; import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.virtual.V8VirtualValue; import java.util.Objects; @@ -112,7 +114,6 @@ public class V8ValueTypedArray extends V8ValueObject implements IV8ValueTypedArr * @since 0.7.2 */ public static final int ZERO_BYTE_PER_VALUE = 0; - /** * The Size in bytes. * @@ -253,6 +254,14 @@ public boolean fromShorts(short[] shorts) throws JavetException { return false; } + @Override + public T get(Object key) throws JavetException { + try (V8VirtualValue virtualKey = new V8VirtualValue( + checkV8Runtime(), OBJECT_CONVERTER, Objects.requireNonNull(key))) { + return v8Runtime.getV8Internal().objectGet(this, virtualKey.get()); + } + } + @Override @CheckReturnValue public V8ValueArrayBuffer getBuffer() throws JavetException { @@ -271,7 +280,7 @@ public int getByteOffset() throws JavetException { @Override public int getLength() throws JavetException { - return checkV8Runtime().getV8Internal().getLength(this); + return checkV8Runtime().getV8Internal().arrayGetLength(this); } @Override diff --git a/src/main/java/com/caoccao/javet/values/reference/V8ValueWeakMap.java b/src/main/java/com/caoccao/javet/values/reference/V8ValueWeakMap.java index 467d0e59b..7d43a5c83 100644 --- a/src/main/java/com/caoccao/javet/values/reference/V8ValueWeakMap.java +++ b/src/main/java/com/caoccao/javet/values/reference/V8ValueWeakMap.java @@ -44,7 +44,7 @@ public boolean delete(Object key) throws JavetException { @CheckReturnValue public T get(String key) throws JavetException { - return checkV8Runtime().getV8Internal().get(this, v8Runtime.createV8ValueString(key)); + return checkV8Runtime().getV8Internal().objectGet(this, v8Runtime.createV8ValueString(key)); } @Override diff --git a/src/test/java/com/caoccao/javet/interop/callback/TestV8FunctionCallback.java b/src/test/java/com/caoccao/javet/interop/callback/TestV8FunctionCallback.java new file mode 100644 index 000000000..fc93322e3 --- /dev/null +++ b/src/test/java/com/caoccao/javet/interop/callback/TestV8FunctionCallback.java @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.interop.callback; + +import com.caoccao.javet.BaseTestJavetRuntime; +import com.caoccao.javet.annotations.V8Function; +import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interfaces.IJavetAnonymous; +import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.primitive.V8ValueInteger; +import com.caoccao.javet.values.reference.V8ValueObject; +import org.junit.jupiter.api.Tag; +import org.junit.jupiter.api.Test; + +import java.util.Arrays; + +import static org.junit.jupiter.api.Assertions.assertEquals; + +public class TestV8FunctionCallback extends BaseTestJavetRuntime { + @Test + @Tag("performance") + public void testReceiveCallback() throws JavetException { + IJavetAnonymous anonymous = new IJavetAnonymous() { + @V8Function + public int test(V8Value... v8Values) { + return v8Values.length; + } + }; + final int argumentCount = 20; + final long loopCount = 200_000L; + V8Value[] arguments = new V8Value[argumentCount]; + Arrays.fill(arguments, v8Runtime.createV8ValueInteger(1)); + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + v8ValueObject.bind(anonymous); + int count = 0; + final long startTime = System.currentTimeMillis(); + for (long i = 0; i < loopCount; i++) { + V8ValueInteger v8ValueInteger = v8ValueObject.invoke("test", arguments); + count += v8ValueInteger.getValue(); + } + final long stopTime = System.currentTimeMillis(); + assertEquals(argumentCount * loopCount, count, "Count should match."); + final long tps = count * 1000L / (stopTime - startTime); + logger.logInfo("{0} calls in {1}ms. TPS is {2}.", count, stopTime - startTime, tps); + } finally { + v8Runtime.lowMemoryNotification(); + } + } +} diff --git a/src/test/java/com/caoccao/javet/interop/converters/TestJavetObjectConverter.java b/src/test/java/com/caoccao/javet/interop/converters/TestJavetObjectConverter.java index d0c1f21c2..d9998da4b 100644 --- a/src/test/java/com/caoccao/javet/interop/converters/TestJavetObjectConverter.java +++ b/src/test/java/com/caoccao/javet/interop/converters/TestJavetObjectConverter.java @@ -48,7 +48,7 @@ public void testAnonymousFunction() throws JavetException { JavetObjectConverter converter = new JavetObjectConverter(); converter.getConfig().setSkipFunctionInObject(false).setExtractFunctionSourceCode(true); Object object = converter.toObject(v8Runtime.getExecutor(codeString).execute(), true); - assertTrue(object instanceof Map); + assertInstanceOf(Map.class, object); Map map = (Map) object; assertEquals(2, map.size()); assertEquals(1, map.get("a")); @@ -83,7 +83,7 @@ public void testArray() throws JavetException { try (V8ValueArray v8ValueArray = v8Runtime.createV8ValueArray()) { v8ValueArray.push("abc"); v8ValueArray.push(123); - List list = (List) converter.toObject(v8ValueArray); + List list = converter.toObject(v8ValueArray); assertEquals(2, list.size()); assertEquals("abc", list.get(0)); assertEquals(123, list.get(1)); @@ -176,7 +176,7 @@ public void testMap() throws JavetException { try (V8ValueMap v8ValueMap = v8Runtime.createV8ValueMap()) { v8ValueMap.set("x", "abc"); assertEquals("abc", v8ValueMap.getString("x")); - JavetEntityMap map = (JavetEntityMap) converter.toObject(v8ValueMap); + JavetEntityMap map = converter.toObject(v8ValueMap); assertEquals(1, map.size()); assertEquals("abc", map.get("x")); } @@ -210,9 +210,11 @@ public void testObject() throws JavetException { v8ValueObject.set("x", "abc"); assertEquals("abc", v8ValueObject.getString("x")); v8ValueObject.setUndefined("y"); + v8ValueObject.set("z", "a"); + assertEquals("a", v8ValueObject.getString("z")); v8ValueObject.setNull("z"); - Map map = (Map) converter.toObject(v8ValueObject); - assertTrue(map instanceof HashMap); + Map map = converter.toObject(v8ValueObject); + assertInstanceOf(HashMap.class, map); assertEquals(2, map.size()); assertEquals("abc", map.get("x")); assertNull(map.get("z")); @@ -231,7 +233,7 @@ public void testSet() throws JavetException { try (V8ValueSet v8ValueSet = v8Runtime.createV8ValueSet()) { v8ValueSet.add(v8Runtime.createV8ValueString("abc")); assertTrue(v8ValueSet.has("abc")); - Set set = (Set) converter.toObject(v8ValueSet); + Set set = converter.toObject(v8ValueSet); assertEquals(1, set.size()); assertTrue(set.contains("abc")); } @@ -298,7 +300,7 @@ public void testTypedArrayByteArray() throws JavetException { try (V8ValueTypedArray v8ValueTypedArray = v8Runtime.createV8ValueTypedArray(V8ValueReferenceType.Int8Array, bytes.length)) { assertTrue(v8ValueTypedArray.fromBytes(bytes)); - byte[] newBytes = (byte[]) converter.toObject(v8ValueTypedArray); + byte[] newBytes = converter.toObject(v8ValueTypedArray); assertArrayEquals(bytes, newBytes); } } @@ -316,7 +318,7 @@ public void testTypedArrayDoubleArray() throws JavetException { try (V8ValueTypedArray v8ValueTypedArray = v8Runtime.createV8ValueTypedArray(V8ValueReferenceType.Float64Array, doubles.length)) { assertTrue(v8ValueTypedArray.fromDoubles(doubles)); - double[] newDoubles = (double[]) converter.toObject(v8ValueTypedArray); + double[] newDoubles = converter.toObject(v8ValueTypedArray); assertArrayEquals(doubles, newDoubles, 0.001D); } } @@ -334,7 +336,7 @@ public void testTypedArrayFloatArray() throws JavetException { try (V8ValueTypedArray v8ValueTypedArray = v8Runtime.createV8ValueTypedArray(V8ValueReferenceType.Float32Array, floats.length)) { assertTrue(v8ValueTypedArray.fromFloats(floats)); - float[] newFloats = (float[]) converter.toObject(v8ValueTypedArray); + float[] newFloats = converter.toObject(v8ValueTypedArray); assertArrayEquals(floats, newFloats, 0.001F); } } @@ -352,7 +354,7 @@ public void testTypedArrayIntegerArray() throws JavetException { try (V8ValueTypedArray v8ValueTypedArray = v8Runtime.createV8ValueTypedArray(V8ValueReferenceType.Int32Array, integers.length)) { assertTrue(v8ValueTypedArray.fromIntegers(integers)); - int[] newIntegers = (int[]) converter.toObject(v8ValueTypedArray); + int[] newIntegers = converter.toObject(v8ValueTypedArray); assertArrayEquals(integers, newIntegers); } } @@ -370,7 +372,7 @@ public void testTypedArrayLongArray() throws JavetException { try (V8ValueTypedArray v8ValueTypedArray = v8Runtime.createV8ValueTypedArray(V8ValueReferenceType.BigInt64Array, longs.length)) { assertTrue(v8ValueTypedArray.fromLongs(longs)); - long[] newLongs = (long[]) converter.toObject(v8ValueTypedArray); + long[] newLongs = converter.toObject(v8ValueTypedArray); assertArrayEquals(longs, newLongs); } } @@ -388,7 +390,7 @@ public void testTypedArrayShortArray() throws JavetException { try (V8ValueTypedArray v8ValueTypedArray = v8Runtime.createV8ValueTypedArray(V8ValueReferenceType.Int16Array, shorts.length)) { assertTrue(v8ValueTypedArray.fromShorts(shorts)); - short[] newShorts = (short[]) converter.toObject(v8ValueTypedArray); + short[] newShorts = converter.toObject(v8ValueTypedArray); assertArrayEquals(shorts, newShorts); } } diff --git a/src/test/java/com/caoccao/javet/interop/converters/TestJavetPrimitiveConverter.java b/src/test/java/com/caoccao/javet/interop/converters/TestJavetPrimitiveConverter.java index ae070655a..72cf33422 100644 --- a/src/test/java/com/caoccao/javet/interop/converters/TestJavetPrimitiveConverter.java +++ b/src/test/java/com/caoccao/javet/interop/converters/TestJavetPrimitiveConverter.java @@ -194,42 +194,42 @@ public void testOptional() throws JavetException { V8Value v8Value; // Boolean v8Value = converter.toV8Value(v8Runtime, Optional.of(true)); - assertTrue(v8Value instanceof V8ValueBoolean); + assertInstanceOf(V8ValueBoolean.class, v8Value); assertTrue(((V8ValueBoolean) v8Value).getValue()); // Double v8Value = converter.toV8Value(v8Runtime, Optional.of(1.23D)); - assertTrue(v8Value instanceof V8ValueDouble); + assertInstanceOf(V8ValueDouble.class, v8Value); assertEquals(1.23D, ((V8ValueDouble) v8Value).getValue(), 0.0001D); // Integer v8Value = converter.toV8Value(v8Runtime, Optional.of(1)); - assertTrue(v8Value instanceof V8ValueInteger); + assertInstanceOf(V8ValueInteger.class, v8Value); assertEquals(1, ((V8ValueInteger) v8Value).getValue()); // Long v8Value = converter.toV8Value(v8Runtime, Optional.of(Long.MAX_VALUE)); - assertTrue(v8Value instanceof V8ValueLong); + assertInstanceOf(V8ValueLong.class, v8Value); assertEquals(Long.MAX_VALUE, ((V8ValueLong) v8Value).getValue()); // String v8Value = converter.toV8Value(v8Runtime, Optional.of("a")); - assertTrue(v8Value instanceof V8ValueString); + assertInstanceOf(V8ValueString.class, v8Value); assertEquals("a", ((V8ValueString) v8Value).getValue()); // ZonedDateTime ZonedDateTime zonedDateTime = ZonedDateTime.now(); v8Value = converter.toV8Value(v8Runtime, Optional.of(zonedDateTime)); - assertTrue(v8Value instanceof V8ValueZonedDateTime); + assertInstanceOf(V8ValueZonedDateTime.class, v8Value); assertEquals( zonedDateTime.toInstant().toEpochMilli(), ((V8ValueZonedDateTime) v8Value).getValue().toInstant().toEpochMilli()); // int v8Value = converter.toV8Value(v8Runtime, OptionalInt.of(1)); - assertTrue(v8Value instanceof V8ValueInteger); + assertInstanceOf(V8ValueInteger.class, v8Value); assertEquals(1, ((V8ValueInteger) v8Value).getValue()); // double v8Value = converter.toV8Value(v8Runtime, OptionalDouble.of(1.23D)); - assertTrue(v8Value instanceof V8ValueDouble); + assertInstanceOf(V8ValueDouble.class, v8Value); assertEquals(1.23D, ((V8ValueDouble) v8Value).getValue(), 0.0001D); // long v8Value = converter.toV8Value(v8Runtime, OptionalLong.of(1L)); - assertTrue(v8Value instanceof V8ValueLong); + assertInstanceOf(V8ValueLong.class, v8Value); assertEquals(1L, ((V8ValueLong) v8Value).getValue()); } diff --git a/src/test/java/com/caoccao/javet/interop/converters/TestJavetProxyConverter.java b/src/test/java/com/caoccao/javet/interop/converters/TestJavetProxyConverter.java index 5c95532e3..753812014 100644 --- a/src/test/java/com/caoccao/javet/interop/converters/TestJavetProxyConverter.java +++ b/src/test/java/com/caoccao/javet/interop/converters/TestJavetProxyConverter.java @@ -26,18 +26,31 @@ import com.caoccao.javet.exceptions.JavetExecutionException; import com.caoccao.javet.interfaces.IJavetAnonymous; import com.caoccao.javet.interfaces.IJavetClosable; -import com.caoccao.javet.interop.proxy.JavetDynamicObjectFactory; +import com.caoccao.javet.interfaces.IJavetUniFunction; +import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.callback.IJavetDirectCallable; +import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; +import com.caoccao.javet.interop.proxy.IJavetDirectProxyHandler; +import com.caoccao.javet.interop.proxy.JavetReflectionObjectFactory; import com.caoccao.javet.mock.MockCallbackReceiver; +import com.caoccao.javet.mock.MockDirectProxyFunctionHandler; +import com.caoccao.javet.mock.MockDirectProxyObjectHandler; import com.caoccao.javet.utils.JavetDateTimeUtils; import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.primitive.V8ValueInteger; import com.caoccao.javet.values.primitive.V8ValueString; +import com.caoccao.javet.values.primitive.V8ValueUndefined; import com.caoccao.javet.values.primitive.V8ValueZonedDateTime; +import com.caoccao.javet.values.reference.V8ValueFunction; import com.caoccao.javet.values.reference.V8ValueObject; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Tag; import org.junit.jupiter.api.Test; import java.io.File; +import java.io.IOException; import java.nio.file.Path; import java.text.MessageFormat; import java.time.ZonedDateTime; @@ -275,7 +288,7 @@ public void testClassForName() throws JavetException { "Column: 6, 7\n" + "Position: 6, 7", e.getScriptingError().toString()); - assertTrue(e.getCause().getCause() instanceof ClassNotFoundException); + assertInstanceOf(ClassNotFoundException.class, e.getCause().getCause()); } v8Runtime.getGlobalObject().delete("Class"); } @@ -291,6 +304,66 @@ public void testConstructor() throws JavetException { v8Runtime.getGlobalObject().delete("StringBuilder"); } + @Test + public void testDirectProxyFunctionHandler() throws JavetException { + int expectedCallCount = 0; + MockDirectProxyFunctionHandler handler = new MockDirectProxyFunctionHandler(); + v8Runtime.getGlobalObject().set("a", handler); + // Test apply(). + assertEquals(6, v8Runtime.getExecutor("a(1,2,3);").executeInteger()); + assertEquals(++expectedCallCount, handler.getCallCount()); + v8Runtime.getGlobalObject().delete("a"); + } + + @Test + public void testDirectProxyObjectHandler() throws JavetException { + int expectedCallCount = 0; + MockDirectProxyObjectHandler handler = new MockDirectProxyObjectHandler(); + v8Runtime.getGlobalObject().set("a", handler); + // Test get() and set(). + try (V8Value v8Value = v8Runtime.getExecutor("a.z;").execute()) { + assertInstanceOf(V8ValueUndefined.class, v8Value); + assertEquals(++expectedCallCount, handler.getCallCount()); + } + assertEquals(0, v8Runtime.getExecutor("a.x;").executeInteger()); + assertEquals(++expectedCallCount, handler.getCallCount()); + assertEquals(0, v8Runtime.getExecutor("a.y;").executeInteger()); + assertEquals(++expectedCallCount, handler.getCallCount()); + assertEquals(3, v8Runtime.getExecutor("a.x = 3; a.x;").executeInteger()); + assertEquals(3, handler.getX()); + ++expectedCallCount; + assertEquals(++expectedCallCount, handler.getCallCount()); + assertEquals(5, v8Runtime.getExecutor("a.y = 5; a.y;").executeInteger()); + assertEquals(5, handler.getY()); + ++expectedCallCount; + assertEquals(++expectedCallCount, handler.getCallCount()); + // Test function get(). + assertTrue(v8Runtime.getExecutor("a.increaseX();").executeBoolean()); + assertEquals(4, handler.getX()); + assertEquals(++expectedCallCount, handler.getCallCount()); + try (V8Value v8Value = v8Runtime.getExecutor("a.increaseX;").execute()) { + assertInstanceOf(V8ValueFunction.class, v8Value); + assertEquals(++expectedCallCount, handler.getCallCount()); + } + assertEquals( + MockDirectProxyObjectHandler.class.getSimpleName(), + v8Runtime.getExecutor("'' + a;").executeString()); + assertEquals(++expectedCallCount, handler.getCallCount()); + // Test ownKeys(). + assertEquals( + "[\"increaseX\",\"x\",\"y\"]", + v8Runtime.getExecutor("JSON.stringify(Object.getOwnPropertyNames(a));").executeString()); + assertEquals(++expectedCallCount, handler.getCallCount()); + // Test has(). + assertFalse(v8Runtime.getExecutor("'z' in a;").executeBoolean()); + assertEquals(++expectedCallCount, handler.getCallCount()); + assertTrue(v8Runtime.getExecutor("'x' in a;").executeBoolean()); + assertEquals(++expectedCallCount, handler.getCallCount()); + assertTrue(v8Runtime.getExecutor("'y' in a;").executeBoolean()); + assertEquals(++expectedCallCount, handler.getCallCount()); + v8Runtime.getGlobalObject().delete("a"); + } + @Test public void testDouble() throws JavetException { v8Runtime.getGlobalObject().set("a", anonymous); @@ -314,7 +387,7 @@ public void test(DynamicClassAutoCloseable mockedDynamicClass) throws Exception } }; try { - javetProxyConverter.getConfig().setDynamicObjectFactory(JavetDynamicObjectFactory.getInstance()); + javetProxyConverter.getConfig().setReflectionObjectFactory(JavetReflectionObjectFactory.getInstance()); v8Runtime.getGlobalObject().set("a", anonymous); String codeString = "a.test({\n" + " add: (a, b) => a + b,\n" + @@ -322,7 +395,7 @@ public void test(DynamicClassAutoCloseable mockedDynamicClass) throws Exception v8Runtime.getExecutor(codeString).executeVoid(); v8Runtime.getGlobalObject().delete("a"); } finally { - javetProxyConverter.getConfig().setDynamicObjectFactory(null); + javetProxyConverter.getConfig().setReflectionObjectFactory(null); } } @@ -352,7 +425,7 @@ public void test(DynamicClassForceCloseable mockedDynamicClass) throws Exception } }; try { - javetProxyConverter.getConfig().setDynamicObjectFactory(JavetDynamicObjectFactory.getInstance()); + javetProxyConverter.getConfig().setReflectionObjectFactory(JavetReflectionObjectFactory.getInstance()); v8Runtime.getGlobalObject().set("a", anonymous); String codeString = "a.test({\n" + " add: (a, b) => a + b,\n" + @@ -366,7 +439,7 @@ public void test(DynamicClassForceCloseable mockedDynamicClass) throws Exception v8Runtime.getExecutor(codeString).executeVoid(); v8Runtime.getGlobalObject().delete("a"); } finally { - javetProxyConverter.getConfig().setDynamicObjectFactory(null); + javetProxyConverter.getConfig().setReflectionObjectFactory(null); } } @@ -399,8 +472,8 @@ public void throwNullPointerException() { assertEquals( "Error: Callback throwNullPointerException failed with error message abc", e.getMessage()); - assertTrue(e.getCause() instanceof JavetException); - assertTrue(e.getCause().getCause() instanceof NullPointerException); + assertInstanceOf(JavetException.class, e.getCause()); + assertInstanceOf(NullPointerException.class, e.getCause().getCause()); assertEquals("abc", e.getCause().getCause().getMessage()); } finally { v8Runtime.getGlobalObject().delete("a"); @@ -576,13 +649,87 @@ public void testPath() throws JavetException { @Test public void testPattern() throws JavetException { v8Runtime.getGlobalObject().set("Pattern", Pattern.class); - assertTrue(v8Runtime.getExecutor("let p = Pattern.compile('^\\\\d+$'); p;").executeObject() instanceof Pattern); + assertInstanceOf(Pattern.class, v8Runtime.getExecutor("let p = Pattern.compile('^\\\\d+$'); p;").executeObject()); assertTrue(v8Runtime.getExecutor("p.matcher('123').matches();").executeBoolean()); assertFalse(v8Runtime.getExecutor("p.matcher('a123').matches();").executeBoolean()); v8Runtime.getGlobalObject().delete("Pattern"); v8Runtime.getExecutor("p = undefined;").executeVoid(); } + @Test + @Tag("performance") + public void testPerformanceBetweenReflectionAndDirectProxies() throws Exception { + final int v8Iterations = 100_000; + IJavetAnonymous reflectionObject = new IJavetAnonymous() { + public int add(int a, int b) { + return a + b; + } + }; + IJavetDirectProxyHandler directObject = new IJavetDirectProxyHandler() { + private Map> stringGetterMap; + private V8Runtime v8Runtime; + + public V8Value add(V8Value... v8Values) throws JavetException { + int a = ((V8ValueInteger) v8Values[0]).toPrimitive(); + int b = ((V8ValueInteger) v8Values[1]).toPrimitive(); + return v8Runtime.createV8ValueInteger(a + b); + } + + @Override + public V8Runtime getV8Runtime() { + return v8Runtime; + } + + @Override + public Map> proxyGetStringGetterMap() { + if (stringGetterMap == null) { + stringGetterMap = new HashMap<>(); + stringGetterMap.put("add", (propertyName) -> v8Runtime.createV8ValueFunction( + new JavetCallbackContext( + propertyName, + JavetCallbackType.DirectCallNoThisAndResult, + (IJavetDirectCallable.NoThisAndResult) this::add))); + } + return stringGetterMap; + } + + @Override + public void setV8Runtime(V8Runtime v8Runtime) { + this.v8Runtime = v8Runtime; + } + }; + System.gc(); + try { + v8Runtime.getGlobalObject().set("a", reflectionObject); + assertEquals(3, v8Runtime.getExecutor("a.add(1, 2);").executeInteger()); + final long startTime = System.currentTimeMillis(); + v8Runtime.getExecutor("for (let i = 0; i < " + v8Iterations + "; ++i) a.add(1, 2);").executeVoid(); + final long stopTime = System.currentTimeMillis(); + final long tps = v8Iterations * 1000L / (stopTime - startTime); + logger.logInfo( + "{0} reflection proxy calls via V8 completed in {1}ms with TPS {2}.", + v8Iterations, stopTime - startTime, tps); + v8Runtime.getGlobalObject().delete("a"); + } finally { + v8Runtime.lowMemoryNotification(); + } + System.gc(); + try { + v8Runtime.getGlobalObject().set("a", directObject); + assertEquals(3, v8Runtime.getExecutor("a.add(1, 2);").executeInteger()); + final long startTime = System.currentTimeMillis(); + v8Runtime.getExecutor("for (let i = 0; i < " + v8Iterations + "; ++i) a.add(1, 2);").executeVoid(); + final long stopTime = System.currentTimeMillis(); + final long tps = v8Iterations * 1000L / (stopTime - startTime); + logger.logInfo( + "{0} direct proxy calls via V8 completed in {1}ms with TPS {2}.", + v8Iterations, stopTime - startTime, tps); + v8Runtime.getGlobalObject().delete("a"); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + @Test public void testSet() throws JavetException { try { diff --git a/src/test/java/com/caoccao/javet/interop/engine/TestPerformance.java b/src/test/java/com/caoccao/javet/interop/engine/TestJavetEnginePerformance.java similarity index 99% rename from src/test/java/com/caoccao/javet/interop/engine/TestPerformance.java rename to src/test/java/com/caoccao/javet/interop/engine/TestJavetEnginePerformance.java index d91f45bfe..d918b82d3 100644 --- a/src/test/java/com/caoccao/javet/interop/engine/TestPerformance.java +++ b/src/test/java/com/caoccao/javet/interop/engine/TestJavetEnginePerformance.java @@ -37,7 +37,7 @@ import static org.junit.jupiter.api.Assertions.assertEquals; -public class TestPerformance extends BaseTestJavetPool { +public class TestJavetEnginePerformance extends BaseTestJavetPool { public static final String PREFIX_NODE = "Node "; public static final String PREFIX_V8 = "V8 "; diff --git a/src/test/java/com/caoccao/javet/interop/proxy/JavetDynamicObjectFactory.java b/src/test/java/com/caoccao/javet/interop/proxy/JavetReflectionObjectFactory.java similarity index 94% rename from src/test/java/com/caoccao/javet/interop/proxy/JavetDynamicObjectFactory.java rename to src/test/java/com/caoccao/javet/interop/proxy/JavetReflectionObjectFactory.java index 693d4443c..cf0dc5423 100644 --- a/src/test/java/com/caoccao/javet/interop/proxy/JavetDynamicObjectFactory.java +++ b/src/test/java/com/caoccao/javet/interop/proxy/JavetReflectionObjectFactory.java @@ -43,11 +43,11 @@ * * @since 2.0.1 */ -public final class JavetDynamicObjectFactory implements IJavetDynamicObjectFactory { - private static final JavetDynamicObjectFactory instance = new JavetDynamicObjectFactory(); +public final class JavetReflectionObjectFactory implements IJavetReflectionObjectFactory { + private static final JavetReflectionObjectFactory instance = new JavetReflectionObjectFactory(); private final IJavetLogger logger; - private JavetDynamicObjectFactory() { + private JavetReflectionObjectFactory() { logger = new JavetDefaultLogger(getClass().getName()); } @@ -57,7 +57,7 @@ private JavetDynamicObjectFactory() { * @return the instance * @since 2.0.1 */ - public static JavetDynamicObjectFactory getInstance() { + public static JavetReflectionObjectFactory getInstance() { return instance; } diff --git a/src/test/java/com/caoccao/javet/mock/MockDirectProxyFunctionHandler.java b/src/test/java/com/caoccao/javet/mock/MockDirectProxyFunctionHandler.java new file mode 100644 index 000000000..d8247bc55 --- /dev/null +++ b/src/test/java/com/caoccao/javet/mock/MockDirectProxyFunctionHandler.java @@ -0,0 +1,43 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.mock; + +import com.caoccao.javet.annotations.V8Convert; +import com.caoccao.javet.enums.V8ProxyMode; +import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.primitive.V8ValueInteger; +import com.caoccao.javet.values.reference.V8ValueArray; + +import java.io.IOException; +import java.util.concurrent.atomic.AtomicInteger; + +@V8Convert(proxyMode = V8ProxyMode.Function) +public class MockDirectProxyFunctionHandler extends MockDirectProxyObjectHandler { + @Override + public V8Value proxyApply(V8Value target, V8Value thisObject, V8ValueArray arguments) + throws JavetException, IOException { + ++callCount; + AtomicInteger atomicInteger = new AtomicInteger(); + arguments.forEach(v8Value -> { + if (v8Value instanceof V8ValueInteger) { + atomicInteger.addAndGet(((V8ValueInteger) v8Value).toPrimitive()); + } + }); + return v8Runtime.createV8ValueInteger(atomicInteger.get()); + } +} diff --git a/src/test/java/com/caoccao/javet/mock/MockDirectProxyObjectHandler.java b/src/test/java/com/caoccao/javet/mock/MockDirectProxyObjectHandler.java new file mode 100644 index 000000000..bfedec8f7 --- /dev/null +++ b/src/test/java/com/caoccao/javet/mock/MockDirectProxyObjectHandler.java @@ -0,0 +1,150 @@ +/* + * Copyright (c) 2023. caoccao.com Sam Cao + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.caoccao.javet.mock; + +import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.interfaces.IJavetBiFunction; +import com.caoccao.javet.interfaces.IJavetUniFunction; +import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.callback.IJavetDirectCallable; +import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; +import com.caoccao.javet.interop.proxy.IJavetDirectProxyHandler; +import com.caoccao.javet.values.V8Value; +import com.caoccao.javet.values.primitive.V8ValueBoolean; +import com.caoccao.javet.values.primitive.V8ValueInteger; +import com.caoccao.javet.values.reference.V8ValueArray; + +import java.io.IOException; +import java.util.HashMap; +import java.util.Map; + +public class MockDirectProxyObjectHandler implements IJavetDirectProxyHandler { + protected int callCount; + protected Map> stringGetterMap; + protected Map> stringSetterMap; + protected V8Runtime v8Runtime; + protected int x; + protected int y; + + public MockDirectProxyObjectHandler() { + callCount = 0; + stringGetterMap = null; + stringSetterMap = null; + x = 0; + y = 0; + } + + public int getCallCount() { + return callCount; + } + + @Override + public V8Runtime getV8Runtime() { + return v8Runtime; + } + + public int getX() { + return x; + } + + public int getY() { + return y; + } + + public V8Value increaseX(V8Value... v8Values) throws JavetException { + x++; + return v8Runtime.createV8ValueBoolean(true); + } + + @Override + public V8Value proxyGet(V8Value target, V8Value property, V8Value receiver) throws JavetException, IOException { + ++callCount; + return IJavetDirectProxyHandler.super.proxyGet(target, property, receiver); + } + + @Override + public Map> proxyGetStringGetterMap() { + if (stringGetterMap == null) { + stringGetterMap = new HashMap<>(); + stringGetterMap.put("x", (propertyName) -> v8Runtime.createV8ValueInteger(getX())); + stringGetterMap.put("y", (propertyName) -> v8Runtime.createV8ValueInteger(getY())); + stringGetterMap.put("increaseX", (propertyName) -> v8Runtime.createV8ValueFunction( + new JavetCallbackContext( + propertyName, + JavetCallbackType.DirectCallNoThisAndResult, + (IJavetDirectCallable.NoThisAndResult) this::increaseX))); + } + return stringGetterMap; + } + + @Override + public Map> proxyGetStringSetterMap() { + if (stringSetterMap == null) { + stringSetterMap = new HashMap<>(); + stringSetterMap.put("x", (propertyName, propertyValue) -> { + if (propertyValue instanceof V8ValueInteger) { + x = ((V8ValueInteger) propertyValue).toPrimitive(); + return true; + } + return false; + }); + stringSetterMap.put("y", (propertyName, propertyValue) -> { + if (propertyValue instanceof V8ValueInteger) { + y = ((V8ValueInteger) propertyValue).toPrimitive(); + return true; + } + return false; + }); + } + return stringSetterMap; + } + + @Override + public V8ValueBoolean proxyHas(V8Value target, V8Value property) throws JavetException, IOException { + ++callCount; + return IJavetDirectProxyHandler.super.proxyHas(target, property); + } + + @Override + public V8ValueArray proxyOwnKeys(V8Value target) throws JavetException, IOException { + ++callCount; + return IJavetDirectProxyHandler.super.proxyOwnKeys(target); + } + + @Override + public V8ValueBoolean proxySet(V8Value target, V8Value propertyKey, V8Value propertyValue, V8Value receiver) + throws JavetException, IOException { + ++callCount; + return IJavetDirectProxyHandler.super.proxySet(target, propertyKey, propertyValue, receiver); + } + + @Override + public void setV8Runtime(V8Runtime v8Runtime) { + this.v8Runtime = v8Runtime; + } + + @Override + public V8Value symbolToPrimitive(V8Value... v8Values) throws JavetException, IOException { + return v8Runtime.createV8ValueString(toString()); + } + + @Override + public String toString() { + return getClass().getSimpleName(); + } +} diff --git a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueArray.java b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueArray.java index 9fce9c8fa..feec0a429 100644 --- a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueArray.java +++ b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueArray.java @@ -18,12 +18,16 @@ import com.caoccao.javet.BaseTestJavetRuntime; import com.caoccao.javet.exceptions.JavetException; +import com.caoccao.javet.utils.JavetResourceUtils; +import com.caoccao.javet.values.V8Value; import com.caoccao.javet.values.primitive.*; +import org.junit.jupiter.api.Tag; import org.junit.jupiter.api.Test; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.ValueSource; import java.time.ZoneId; +import java.util.Arrays; import java.util.List; import java.util.concurrent.atomic.AtomicInteger; @@ -77,6 +81,23 @@ public void testGet() throws JavetException { assertEquals(2, v8Runtime.getReferenceCount()); } assertEquals(1, v8Runtime.getReferenceCount()); + V8Value[] v8Values = v8ValueArray.batchGet(); + assertEquals(6, v8Values.length); + assertEquals(1, ((V8ValueInteger) v8Values[0]).getValue()); + assertEquals("2", ((V8ValueString) v8Values[1]).getValue()); + assertEquals(3L, ((V8ValueLong) v8Values[2]).getValue()); + assertTrue(((V8ValueBoolean) v8Values[3]).getValue()); + assertEquals(1.23, ((V8ValueDouble) v8Values[4]).getValue(), 0.001D); + assertInstanceOf(V8ValueArray.class, v8Values[5]); + assertEquals(2, v8Runtime.getReferenceCount()); + JavetResourceUtils.safeClose(v8Values); + assertEquals(1, v8Runtime.getReferenceCount()); + Arrays.fill(v8Values, null); + assertEquals(0, v8ValueArray.batchGet(v8Values, 2, 1), "The actual length should be 0."); + assertEquals(2, v8ValueArray.batchGet(v8Values, 1, 3)); + assertEquals("2", ((V8ValueString) v8Values[0]).getValue()); + assertEquals(3L, ((V8ValueLong) v8Values[1]).getValue()); + JavetResourceUtils.safeClose( v8Values); } } @@ -118,15 +139,47 @@ public void testNestedArray() throws JavetException { } } + @Test + @Tag("performance") + public void testPerformancePush() throws JavetException { + final int itemCount = 1000; + final int iterations = 1000; + // Test push one by one. + { + final long startTime = System.currentTimeMillis(); + for (int i = 0; i < iterations; i++) { + try (V8ValueArray v8ValueArray = v8Runtime.createV8ValueArray()) { + for (int j = 0; j < itemCount; j++) { + v8ValueArray.push(1); + } + } + } + final long stopTime = System.currentTimeMillis(); + final long tps = itemCount * iterations * 1000 / (stopTime - startTime); + logger.logInfo("Array push one by one: {0} tps.", tps); + } + // Test push by batch. + { + final long startTime = System.currentTimeMillis(); + Object[] items = new Object[itemCount]; + Arrays.fill(items, 1); + for (int i = 0; i < iterations; i++) { + try (V8ValueArray v8ValueArray = v8Runtime.createV8ValueArray()) { + v8ValueArray.push(items); + } + } + final long stopTime = System.currentTimeMillis(); + final long tps = itemCount * iterations * 1000 / (stopTime - startTime); + logger.logInfo("Array push in a batch: {0} tps.", tps); + } + } + @Test public void testPushPop() throws JavetException { try (V8ValueArray v8ValueArray = v8Runtime.getExecutor("[]").execute()) { assertEquals(0, v8ValueArray.getLength()); assertEquals(1, v8ValueArray.push(true)); - assertEquals(2, v8ValueArray.push(1.23)); - assertEquals(3, v8ValueArray.push(4)); - assertEquals(4, v8ValueArray.push(5L)); - assertEquals(5, v8ValueArray.push("x")); + assertEquals(5, v8ValueArray.push(1.23, 4, 5L, "x")); assertEquals(6, v8ValueArray.pushNull()); assertEquals(7, v8ValueArray.pushUndefined()); assertEquals(7, v8ValueArray.getLength()); diff --git a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueFunction.java b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueFunction.java index 7e9a9885e..f810e16ba 100644 --- a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueFunction.java +++ b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueFunction.java @@ -19,12 +19,15 @@ import com.caoccao.javet.BaseTestJavetRuntime; import com.caoccao.javet.annotations.V8Function; import com.caoccao.javet.enums.V8ScopeType; +import com.caoccao.javet.enums.V8ValueSymbolType; import com.caoccao.javet.exceptions.JavetError; import com.caoccao.javet.exceptions.JavetException; import com.caoccao.javet.exceptions.JavetExecutionException; import com.caoccao.javet.interfaces.IJavetAnonymous; import com.caoccao.javet.interop.V8Runtime; +import com.caoccao.javet.interop.callback.IJavetDirectCallable; import com.caoccao.javet.interop.callback.JavetCallbackContext; +import com.caoccao.javet.interop.callback.JavetCallbackType; import com.caoccao.javet.interop.engine.IJavetEngine; import com.caoccao.javet.interop.engine.IJavetEnginePool; import com.caoccao.javet.interop.engine.JavetEnginePool; @@ -34,10 +37,12 @@ import com.caoccao.javet.values.V8Value; import com.caoccao.javet.values.primitive.V8ValueInteger; import com.caoccao.javet.values.primitive.V8ValueString; +import com.caoccao.javet.values.primitive.V8ValueUndefined; import org.junit.jupiter.api.Tag; import org.junit.jupiter.api.Test; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.ValueSource; +import org.opentest4j.AssertionFailedError; import java.text.MessageFormat; import java.time.ZoneId; @@ -189,7 +194,7 @@ public void testAnonymousFunction() throws JavetException { String codeString = "() => '123測試'"; try (V8Value v8Value = v8Runtime.getExecutor(codeString).execute()) { assertNotNull(v8Value); - assertTrue(v8Value instanceof V8ValueFunction); + assertInstanceOf(V8ValueFunction.class, v8Value); V8ValueFunction v8ValueFunction = (V8ValueFunction) v8Value; assertTrue(v8ValueFunction.getJSFunctionType().isUserDefined()); assertEquals(codeString, v8ValueFunction.toString()); @@ -292,7 +297,10 @@ public void testCallObject() throws JavetException { public void testCallbackBlankWithThis() throws JavetException, NoSuchMethodException { MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("echoThis", true), true); + "echoThis", + mockCallbackReceiver, + mockCallbackReceiver.getMethod("echoThis", true), + true); V8ValueObject globalObject = v8Runtime.getGlobalObject(); V8ValueFunction v8ValueFunction = v8Runtime.createV8ValueFunction(javetCallbackContext); try (V8ValueObject a = v8Runtime.createV8ValueObject()) { @@ -320,7 +328,9 @@ public void testCallbackBlankWithThis() throws JavetException, NoSuchMethodExcep public void testCallbackBlankWithoutThis() throws JavetException, NoSuchMethodException { MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("blank")); + "blank", + mockCallbackReceiver, + mockCallbackReceiver.getMethod("blank")); V8ValueObject globalObject = v8Runtime.getGlobalObject(); V8ValueFunction v8ValueFunction = v8Runtime.createV8ValueFunction(javetCallbackContext); try (V8ValueObject a = v8Runtime.createV8ValueObject()) { @@ -348,7 +358,10 @@ public void testCallbackEchoLILOWithThis() throws JavetException, NoSuchMethodEx assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethodVarargs("echoThis", true), true); + "echoThis", + mockCallbackReceiver, + mockCallbackReceiver.getMethodVarargs("echoThis", true), + true); V8ValueObject globalObject = v8Runtime.getGlobalObject(); try (V8ValueFunction v8ValueFunction = v8Runtime.createV8ValueFunction(javetCallbackContext)) { assertEquals(1, v8Runtime.getReferenceCount()); @@ -378,7 +391,9 @@ public void testCallbackEchoLILOWithoutThis() throws JavetException, NoSuchMetho assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethodVarargs("echo")); + "echo", + mockCallbackReceiver, + mockCallbackReceiver.getMethodVarargs("echo")); V8ValueObject globalObject = v8Runtime.getGlobalObject(); try (V8ValueFunction v8ValueFunction = v8Runtime.createV8ValueFunction(javetCallbackContext)) { assertEquals(1, v8Runtime.getReferenceCount()); @@ -403,7 +418,10 @@ public void testCallbackEchoStringWithThis() throws JavetException, NoSuchMethod assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("echoThisString", V8Value.class, String.class), true); + "echoThisString", + mockCallbackReceiver, + mockCallbackReceiver.getMethod("echoThisString", V8Value.class, String.class), + true); V8ValueObject globalObject = v8Runtime.getGlobalObject(); try (V8ValueFunction v8ValueFunction = v8Runtime.createV8ValueFunction(javetCallbackContext)) { assertEquals(1, v8Runtime.getReferenceCount()); @@ -428,7 +446,9 @@ public void testCallbackEchoStringWithoutThis() throws JavetException, NoSuchMet assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("echoString", String.class)); + "echoString", + mockCallbackReceiver, + mockCallbackReceiver.getMethod("echoString", String.class)); V8ValueObject globalObject = v8Runtime.getGlobalObject(); try (V8ValueFunction v8ValueFunction = v8Runtime.createV8ValueFunction(javetCallbackContext)) { assertEquals(1, v8Runtime.getReferenceCount()); @@ -439,8 +459,10 @@ public void testCallbackEchoStringWithoutThis() throws JavetException, NoSuchMet assertTrue(mockCallbackReceiver.isCalled()); globalObject.delete("echoString"); javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("echoString", V8Value[].class)); - globalObject.bindFunction("echoString", javetCallbackContext); + "echoString", + mockCallbackReceiver, + mockCallbackReceiver.getMethod("echoString", V8Value[].class)); + globalObject.bindFunction(javetCallbackContext); assertEquals("abc", v8Runtime.getExecutor("echoString('abc')").executeString()); assertEquals("abc,def", v8Runtime.getExecutor("echoString('abc', 'def')").executeString()); assertEquals("", v8Runtime.getExecutor("echoString()").executeString()); @@ -453,7 +475,10 @@ public void testCallbackEchoVIVOWithThis() throws JavetException, NoSuchMethodEx assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("echoThis", V8Value.class, V8Value.class), true); + "echoThis", + mockCallbackReceiver, + mockCallbackReceiver.getMethod("echoThis", V8Value.class, V8Value.class), + true); V8ValueObject globalObject = v8Runtime.getGlobalObject(); try (V8ValueFunction v8ValueFunction = v8Runtime.createV8ValueFunction(javetCallbackContext)) { assertEquals(1, v8Runtime.getReferenceCount()); @@ -477,7 +502,9 @@ public void testCallbackEchoVIVOWithoutThis() throws JavetException, NoSuchMetho assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("echo", V8Value.class)); + "echo", + mockCallbackReceiver, + mockCallbackReceiver.getMethod("echo", V8Value.class)); V8ValueObject globalObject = v8Runtime.getGlobalObject(); try (V8ValueFunction v8ValueFunction = v8Runtime.createV8ValueFunction(javetCallbackContext)) { assertEquals(1, v8Runtime.getReferenceCount()); @@ -497,9 +524,11 @@ public void testCallbackEchoVIVOWithoutThis() throws JavetException, NoSuchMetho public void testCallbackError() throws JavetException, NoSuchMethodException { MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("error")); + "testError", + mockCallbackReceiver, + mockCallbackReceiver.getMethod("error")); V8ValueObject globalObject = v8Runtime.getGlobalObject(); - globalObject.bindFunction("testError", javetCallbackContext); + globalObject.bindFunction(javetCallbackContext); assertEquals(0, v8Runtime.getReferenceCount()); assertFalse(mockCallbackReceiver.isCalled()); try { @@ -524,6 +553,7 @@ public void testCallbackJoinIntegerArrayWithThis() throws JavetException, NoSuch assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( + "joinIntegerArrayWithThis", mockCallbackReceiver, mockCallbackReceiver.getMethod( "joinIntegerArrayWithThis", V8ValueObject.class, String.class, Integer[].class), @@ -551,6 +581,7 @@ public void testCallbackJoinWithThis() throws JavetException, NoSuchMethodExcept assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( + "joinWithThis", mockCallbackReceiver, mockCallbackReceiver.getMethod("joinWithThis", V8ValueObject.class, Boolean.class, Double.class, Integer.class, Long.class, @@ -579,9 +610,11 @@ public void testCallbackJoinWithoutThis() throws JavetException, NoSuchMethodExc assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("joinWithoutThis", - Boolean.class, Double.class, Integer.class, Long.class, String.class, ZonedDateTime.class, - V8ValueString.class)); + "joinWithoutThis", + mockCallbackReceiver, + mockCallbackReceiver.getMethod( + "joinWithoutThis", Boolean.class, Double.class, Integer.class, + Long.class, String.class, ZonedDateTime.class, V8ValueString.class)); V8ValueObject globalObject = v8Runtime.getGlobalObject(); try (V8ValueFunction v8ValueFunction = v8Runtime.createV8ValueFunction(javetCallbackContext)) { assertTrue(v8ValueFunction.getJSFunctionType().isAPI()); @@ -603,6 +636,169 @@ public void testCallbackJoinWithoutThis() throws JavetException, NoSuchMethodExc v8Runtime.lowMemoryNotification(); } + @Test + public void testCallbackTypeGetterAndNoThis() throws JavetException { + String functionName = "test"; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + IJavetDirectCallable.GetterAndNoThis callback = () -> v8Runtime.createV8ValueInteger(1); + JavetCallbackContext callbackContext = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallGetterAndNoThis, callback); + v8ValueObject.bindProperty(callbackContext); + assertEquals(1, v8ValueObject.getInteger(functionName)); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + + @Test + public void testCallbackTypeGetterAndThis() throws JavetException { + String functionName = "test"; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + v8ValueObject.set("a", "a"); + IJavetDirectCallable.GetterAndThis callback = (thisObject) -> { + assertInstanceOf(V8ValueObject.class, thisObject); + assertEquals("a", ((V8ValueObject) thisObject).getString("a")); + return v8Runtime.createV8ValueInteger(1); + }; + JavetCallbackContext callbackContext = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallGetterAndThis, callback); + v8ValueObject.bindProperty(callbackContext); + assertEquals(1, v8ValueObject.getInteger(functionName)); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + + @Test + public void testCallbackTypeNoThisAndNoResult() throws JavetException { + String functionName = "test"; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + int[] storage = new int[1]; + IJavetDirectCallable.NoThisAndNoResult callback = (v8Values) -> { + assertEquals(2, v8Values.length); + storage[0] = ((V8ValueInteger) v8Values[0]).getValue() + ((V8ValueInteger) v8Values[1]).getValue(); + }; + JavetCallbackContext callbackContext = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallNoThisAndNoResult, callback); + v8ValueObject.bindFunction(callbackContext); + v8ValueObject.invokeVoid(functionName, 1, 2); + assertEquals(3, storage[0]); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + + @Test + public void testCallbackTypeNoThisAndResult() throws JavetException { + String functionName = "test"; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + IJavetDirectCallable.NoThisAndResult callback = (v8Values) -> { + assertEquals(2, v8Values.length); + return v8Runtime.createV8ValueInteger( + ((V8ValueInteger) v8Values[0]).getValue() + ((V8ValueInteger) v8Values[1]).getValue()); + }; + JavetCallbackContext callbackContext = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallNoThisAndResult, callback); + v8ValueObject.bindFunction(callbackContext); + assertEquals(3, v8ValueObject.invokeInteger(functionName, 1, 2)); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + + @Test + public void testCallbackTypeSetterAndNoThis() throws JavetException { + String functionName = "test"; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + int[] storage = new int[1]; + IJavetDirectCallable.GetterAndNoThis callbackGetter = () -> v8Runtime.createV8ValueInteger(storage[0]); + JavetCallbackContext callbackContextGetter = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallGetterAndNoThis, callbackGetter); + IJavetDirectCallable.SetterAndNoThis callbackSetter = (value) -> { + storage[0] = ((V8ValueInteger) value).getValue(); + return v8Runtime.createV8ValueBoolean(true); + }; + JavetCallbackContext callbackContextSetter = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallSetterAndNoThis, callbackSetter); + v8ValueObject.bindProperty(callbackContextGetter, callbackContextSetter); + assertTrue(v8ValueObject.setInteger(functionName, 2)); + assertEquals(2, v8ValueObject.getInteger(functionName)); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + + @Test + public void testCallbackTypeSetterAndThis() throws JavetException { + String functionName = "test"; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + v8ValueObject.set("a", "a"); + int[] storage = new int[1]; + IJavetDirectCallable.GetterAndThis callbackGetter = (thisObject) -> { + assertInstanceOf(V8ValueObject.class, thisObject); + assertEquals("a", ((V8ValueObject) thisObject).getString("a")); + return v8Runtime.createV8ValueInteger(storage[0]); + }; + JavetCallbackContext callbackContextGetter = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallGetterAndThis, callbackGetter); + IJavetDirectCallable.SetterAndThis callbackSetter = (thisObject, value) -> { + assertInstanceOf(V8ValueObject.class, thisObject); + storage[0] = ((V8ValueInteger) value).getValue(); + return v8Runtime.createV8ValueBoolean(true); + }; + JavetCallbackContext callbackContextSetter = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallSetterAndThis, callbackSetter); + v8ValueObject.bindProperty(callbackContextGetter, callbackContextSetter); + assertTrue(v8ValueObject.setInteger(functionName, 2)); + assertEquals(2, v8ValueObject.getInteger(functionName)); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + + @Test + public void testCallbackTypeThisAndNoResult() throws JavetException { + String functionName = "test"; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + v8ValueObject.set("a", "a"); + int[] storage = new int[1]; + IJavetDirectCallable.ThisAndNoResult callback = (thisObject, v8Values) -> { + assertInstanceOf(V8ValueObject.class, thisObject); + assertEquals("a", ((V8ValueObject) thisObject).getString("a")); + assertEquals(2, v8Values.length); + storage[0] = ((V8ValueInteger) v8Values[0]).getValue() + ((V8ValueInteger) v8Values[1]).getValue(); + }; + JavetCallbackContext callbackContext = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallThisAndNoResult, callback); + v8ValueObject.bindFunction(callbackContext); + assertInstanceOf(V8ValueUndefined.class, v8ValueObject.invoke(functionName, 1, 2)); + assertEquals(3, storage[0]); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + + @Test + public void testCallbackTypeThisAndResult() throws JavetException { + String functionName = "test"; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + v8ValueObject.set("a", "a"); + IJavetDirectCallable.ThisAndResult callback = (thisObject, v8Values) -> { + assertInstanceOf(V8ValueObject.class, thisObject); + assertEquals("a", ((V8ValueObject) thisObject).getString("a")); + assertEquals(2, v8Values.length); + return v8Runtime.createV8ValueInteger( + ((V8ValueInteger) v8Values[0]).getValue() + ((V8ValueInteger) v8Values[1]).getValue()); + }; + JavetCallbackContext callbackContext = new JavetCallbackContext( + functionName, JavetCallbackType.DirectCallThisAndResult, callback); + v8ValueObject.bindFunction(callbackContext); + assertEquals(3, v8ValueObject.invokeInteger(functionName, 1, 2)); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + @Test public void testCompileV8ValueFunction() throws JavetException { String codeString = "return a + b"; @@ -712,6 +908,136 @@ public void testCopyScopeInfoFrom() throws JavetException { } } + @Test + public void testDirectCallable() throws JavetException { + IJavetDirectCallable directCallable = new IJavetDirectCallable() { + private JavetCallbackContext[] javetCallbackContexts; + private V8Runtime v8Runtime; + private int x; + private int y; + + public V8Value add(V8Value... v8Values) throws JavetException { + ++x; + return v8Runtime.createV8ValueInteger( + ((V8ValueInteger) v8Values[0]).getValue() + ((V8ValueInteger) v8Values[1]).getValue()); + } + + public void assertAdd(V8Value... v8Values) { + ++x; + assertEquals( + ((V8ValueInteger) v8Values[0]).getValue(), + ((V8ValueInteger) v8Values[1]).getValue() + ((V8ValueInteger) v8Values[2]).getValue()); + } + + public void assertSubtract(V8Value thisObject, V8Value... v8Values) { + assertInstanceOf(V8ValueObject.class, thisObject); + ++x; + assertEquals( + ((V8ValueInteger) v8Values[0]).getValue(), + ((V8ValueInteger) v8Values[1]).getValue() - ((V8ValueInteger) v8Values[2]).getValue()); + } + + @Override + public JavetCallbackContext[] getCallbackContexts() { + if (javetCallbackContexts == null) { + javetCallbackContexts = new JavetCallbackContext[]{ + new JavetCallbackContext( + "add", JavetCallbackType.DirectCallNoThisAndResult, + (IJavetDirectCallable.NoThisAndResult) this::add), + new JavetCallbackContext( + "assertAdd", JavetCallbackType.DirectCallNoThisAndNoResult, + (IJavetDirectCallable.NoThisAndNoResult) this::assertAdd), + new JavetCallbackContext( + "subtract", JavetCallbackType.DirectCallThisAndResult, + (IJavetDirectCallable.ThisAndResult) this::subtract), + new JavetCallbackContext( + "assertSubtract", JavetCallbackType.DirectCallThisAndNoResult, + (IJavetDirectCallable.ThisAndNoResult) this::assertSubtract), + new JavetCallbackContext( + "x", JavetCallbackType.DirectCallGetterAndNoThis, + (IJavetDirectCallable.GetterAndNoThis) this::xGet), + new JavetCallbackContext( + "x", JavetCallbackType.DirectCallSetterAndNoThis, + (IJavetDirectCallable.SetterAndNoThis) this::xSet), + new JavetCallbackContext( + "y", JavetCallbackType.DirectCallGetterAndThis, + (IJavetDirectCallable.GetterAndThis) this::yGet), + new JavetCallbackContext( + "y", JavetCallbackType.DirectCallSetterAndThis, + (IJavetDirectCallable.SetterAndThis) this::ySet), + }; + } + return javetCallbackContexts; + } + + @Override + public void setV8Runtime(V8Runtime v8Runtime) { + this.v8Runtime = v8Runtime; + } + + public V8Value subtract(V8Value thisObject, V8Value... v8Values) throws JavetException { + assertInstanceOf(V8ValueObject.class, thisObject); + ++x; + return v8Runtime.createV8ValueInteger( + ((V8ValueInteger) v8Values[0]).getValue() - ((V8ValueInteger) v8Values[1]).getValue()); + } + + public V8Value xGet() throws JavetException { + return v8Runtime.createV8ValueInteger(x); + } + + public V8Value xSet(V8Value v8Value) throws JavetException { + x = ((V8ValueInteger) v8Value).getValue(); + return v8Runtime.createV8ValueBoolean(true); + } + + public V8Value yGet(V8Value thisObject) throws JavetException { + assertInstanceOf(V8ValueObject.class, thisObject); + return v8Runtime.createV8ValueInteger(y); + } + + public V8Value ySet(V8Value thisObject, V8Value v8Value) throws JavetException { + assertInstanceOf(V8ValueObject.class, thisObject); + y = ((V8ValueInteger) v8Value).getValue(); + return v8Runtime.createV8ValueBoolean(true); + } + }; + final int expectedCallbackContextSize = 8; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + assertEquals(expectedCallbackContextSize, v8ValueObject.bind(directCallable).size()); + assertEquals(expectedCallbackContextSize, directCallable.getCallbackContexts().length); + assertTrue(v8ValueObject.setInteger("x", 3)); + assertEquals(3, v8ValueObject.getInteger("x")); + assertTrue(v8ValueObject.setInteger("y", 5)); + assertEquals(5, v8ValueObject.getInteger("y")); + assertEquals(3, v8ValueObject.invokeInteger("add", 1, 2)); + assertEquals(4, v8ValueObject.getInteger("x")); + assertEquals(1, v8ValueObject.invokeInteger("subtract", 2, 1)); + assertEquals(5, v8ValueObject.getInteger("x")); + v8ValueObject.invokeVoid("assertAdd", 3, 1, 2); + assertEquals(6, v8ValueObject.getInteger("x")); + try { + v8ValueObject.invokeVoid("assertAdd", 3, 1, 3); + fail("Failed to throw an exception."); + } catch (JavetExecutionException e) { + assertInstanceOf(AssertionFailedError.class, e.getCause()); + } + assertEquals(7, v8ValueObject.getInteger("x")); + v8ValueObject.invokeVoid("assertSubtract", 1, 2, 1); + assertEquals(8, v8ValueObject.getInteger("x")); + try { + v8ValueObject.invokeVoid("assertSubtract", 0, 2, 1); + fail("Failed to throw an exception."); + } catch (JavetExecutionException e) { + assertInstanceOf(AssertionFailedError.class, e.getCause()); + } + assertEquals(9, v8ValueObject.getInteger("x")); + assertEquals(expectedCallbackContextSize - 2, v8ValueObject.unbind(directCallable)); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + @Test public void testDiscardCompiled() throws JavetException { final int rounds = 3; @@ -1545,17 +1871,80 @@ public OptionalLong test(OptionalLong optionalLong) { } } + @Test + @Tag("performance") + public void testPerformanceBetweenReflectionAndDirectCalls() throws Exception { + final int v8Iterations = 2_000_000; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + IJavetAnonymous anonymous = new IJavetAnonymous() { + @V8Function + public int test(int i) { + return i; + } + }; + v8ValueObject.bind(anonymous); + v8Runtime.getGlobalObject().set("a", v8ValueObject); + final long startTime = System.currentTimeMillis(); + assertEquals(v8Iterations, v8Runtime.getExecutor("let x = 0;\n" + + "for (let i = 0; i < " + v8Iterations + "; ++i)\n" + + " x += a.test(1);\n" + + "x;").executeInteger()); + final long stopTime = System.currentTimeMillis(); + final long tps = v8Iterations * 1000L / (stopTime - startTime); + logger.logInfo( + "{0} reflection calls via V8 completed in {1}ms with TPS {2}.", + v8Iterations, stopTime - startTime, tps); + v8Runtime.getGlobalObject().delete("a"); + } finally { + v8Runtime.lowMemoryNotification(); + } + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + IJavetDirectCallable directCallable = new IJavetDirectCallable() { + @Override + public JavetCallbackContext[] getCallbackContexts() { + return new JavetCallbackContext[]{ + new JavetCallbackContext( + "test", JavetCallbackType.DirectCallNoThisAndResult, + (IJavetDirectCallable.NoThisAndResult) this::test), + }; + } + + public V8Value test(V8Value... v8Values) { + return v8Values[0]; + } + }; + v8ValueObject.bind(directCallable); + v8Runtime.getGlobalObject().set("a", v8ValueObject); + final long startTime = System.currentTimeMillis(); + assertEquals(v8Iterations, v8Runtime.getExecutor("let y = 0;\n" + + "for (let i = 0; i < " + v8Iterations + "; ++i)\n" + + " y += a.test(1);\n" + + "y;").executeInteger()); + final long stopTime = System.currentTimeMillis(); + final long tps = v8Iterations * 1000L / (stopTime - startTime); + logger.logInfo( + "{0} direct calls via V8 completed in {1}ms with TPS {2}.", + v8Iterations, stopTime - startTime, tps); + v8Runtime.getGlobalObject().delete("a"); + } finally { + v8Runtime.lowMemoryNotification(); + } + } + @Test public void testPropertyGetter() throws NoSuchMethodException, JavetException { assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContextGetter = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("getValue")); + "test", + V8ValueSymbolType.None, + mockCallbackReceiver, + mockCallbackReceiver.getMethod("getValue")); V8ValueObject globalObject = v8Runtime.getGlobalObject(); try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { globalObject.set("a", v8ValueObject); mockCallbackReceiver.setValue("abc"); - assertTrue(v8ValueObject.bindProperty("test", javetCallbackContextGetter)); + assertTrue(v8ValueObject.bindProperty(javetCallbackContextGetter)); assertEquals(1, v8Runtime.getReferenceCount()); assertEquals(1, v8Runtime.getCallbackContextCount()); mockCallbackReceiver.setCalled(false); @@ -1578,14 +1967,20 @@ public void testPropertyGetterAndSetter() throws NoSuchMethodException, JavetExc assertEquals(0, v8Runtime.getReferenceCount()); MockCallbackReceiver mockCallbackReceiver = new MockCallbackReceiver(v8Runtime); JavetCallbackContext javetCallbackContextGetter = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("getValue")); + "test", + V8ValueSymbolType.None, + mockCallbackReceiver, + mockCallbackReceiver.getMethod("getValue")); JavetCallbackContext javetCallbackContextSetter = new JavetCallbackContext( - mockCallbackReceiver, mockCallbackReceiver.getMethod("setValue", String.class)); + "setValue", + V8ValueSymbolType.None, + mockCallbackReceiver, + mockCallbackReceiver.getMethod("setValue", String.class)); V8ValueObject globalObject = v8Runtime.getGlobalObject(); try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { globalObject.set("a", v8ValueObject); assertNull(mockCallbackReceiver.getValue()); - assertTrue(v8ValueObject.bindProperty("test", javetCallbackContextGetter, javetCallbackContextSetter)); + assertTrue(v8ValueObject.bindProperty(javetCallbackContextGetter, javetCallbackContextSetter)); assertEquals(1, v8Runtime.getReferenceCount()); assertEquals(2, v8Runtime.getCallbackContextCount()); mockCallbackReceiver.setCalled(false); diff --git a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueMap.java b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueMap.java index 2098698e3..f5d4d16fd 100644 --- a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueMap.java +++ b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueMap.java @@ -28,7 +28,6 @@ import static org.junit.jupiter.api.Assertions.*; -@SuppressWarnings("unchecked") public class TestV8ValueMap extends BaseTestJavetRuntime { @Test public void testForEach() throws JavetException { @@ -130,6 +129,50 @@ public void testGetSetAndDelete() throws JavetException { assertTrue(v8ValueMap.delete("a")); assertTrue(v8ValueMap.delete("b")); assertEquals(0, v8ValueMap.getSize()); + v8ValueMap.setString("d", "1"); + assertEquals("1", v8ValueMap.getString("d")); + assertTrue(v8ValueMap.has("d")); + v8ValueMap.setString("d", null); + assertNull(v8ValueMap.getString("d")); + assertTrue(v8ValueMap.has("d")); + Object[] keysAndValues = new Object[]{"x", 1, "y", 2, "z", 3}; + assertTrue(v8ValueMap.set(keysAndValues)); + for (int i = 0; i < keysAndValues.length / 2; i += 2) { + assertTrue(v8ValueMap.has(keysAndValues[i * 2])); + assertEquals(keysAndValues[i * 2 + 1], v8ValueMap.getInteger(keysAndValues[i * 2])); + } + } + String key = "a"; + try (V8ValueMap v8ValueMap = v8Runtime.createV8ValueMap()) { + for (Boolean value : new Boolean[]{true, false, null}) { + assertTrue(v8ValueMap.setBoolean(key, value)); + assertTrue(v8ValueMap.has(key)); + assertEquals(value, v8ValueMap.getBoolean(key)); + } + } + try (V8ValueMap v8ValueMap = v8Runtime.createV8ValueMap()) { + for (Double value : new Double[]{0.1D, 1.234D, -1.234D, Double.MIN_VALUE, Double.MAX_VALUE}) { + assertTrue(v8ValueMap.setDouble(key, value)); + assertTrue(v8ValueMap.has(key)); + assertEquals(value, v8ValueMap.getDouble(key), 0.001D); + } + assertTrue(v8ValueMap.setDouble(key, null)); + assertTrue(v8ValueMap.has(key)); + assertNull(v8ValueMap.getDouble(key)); + } + try (V8ValueMap v8ValueMap = v8Runtime.createV8ValueMap()) { + for (Integer value : new Integer[]{0, 1, -1, Integer.MIN_VALUE, Integer.MAX_VALUE, null}) { + assertTrue(v8ValueMap.setInteger(key, value)); + assertTrue(v8ValueMap.has(key)); + assertEquals(value, v8ValueMap.getInteger(key)); + } + } + try (V8ValueMap v8ValueMap = v8Runtime.createV8ValueMap()) { + for (Long value : new Long[]{0L, 1L, -1L, Long.MIN_VALUE, Long.MAX_VALUE, null}) { + assertTrue(v8ValueMap.setLong(key, value)); + assertTrue(v8ValueMap.has(key)); + assertEquals(value, v8ValueMap.getLong(key)); + } } } diff --git a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueObject.java b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueObject.java index adc871e28..f532bd282 100644 --- a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueObject.java +++ b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueObject.java @@ -31,12 +31,14 @@ import com.caoccao.javet.values.primitive.V8ValueInteger; import com.caoccao.javet.values.primitive.V8ValueLong; import com.caoccao.javet.values.primitive.V8ValueString; +import org.junit.jupiter.api.Tag; import org.junit.jupiter.api.Test; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.ValueSource; import java.time.ZoneId; import java.time.ZonedDateTime; +import java.util.Arrays; import java.util.List; import java.util.concurrent.atomic.AtomicInteger; @@ -150,7 +152,7 @@ public void testClearWeak() throws JavetException { assertEquals(0, v8Runtime.getReferenceCount()); assertEquals(0L, a.getHandle()); try (V8ValueObject b = globalObject.get("a")) { - assertTrue(b instanceof V8ValueObject); + assertNotNull(b); } } @@ -182,25 +184,25 @@ public void testForEach() throws JavetException { "const a = {'A0': 0, 'A1': 1, 'A2': 2}; a;").execute()) { AtomicInteger count = new AtomicInteger(0); assertEquals(3, v8ValueObject.forEach((V8ValueString key) -> { - assertEquals("A" + Integer.toString(count.getAndIncrement()), key.getValue()); + assertEquals("A" + count.getAndIncrement(), key.getValue()); })); count.set(0); assertEquals(3, v8ValueObject.forEach((V8ValueString key, V8ValueInteger value) -> { - assertEquals("A" + Integer.toString(count.get()), key.getValue()); + assertEquals("A" + count.get(), key.getValue()); assertEquals(count.getAndIncrement(), value.getValue()); })); assertEquals(3, v8ValueObject.forEach((int index, V8ValueString key) -> { - assertEquals("A" + Integer.toString(index), key.getValue()); + assertEquals("A" + index, key.getValue()); })); assertEquals(3, v8ValueObject.forEach((int index, V8ValueString key, V8ValueInteger value) -> { - assertEquals("A" + Integer.toString(index), key.getValue()); + assertEquals("A" + index, key.getValue()); assertEquals(index, value.getValue()); })); } try (V8ValueObject v8ValueObject = v8Runtime.getExecutor( "const b = {'2147483648': '2**31'}; b;").execute()) { assertEquals(1, v8ValueObject.forEach((V8Value key, V8Value value) -> { - assertTrue(key instanceof V8ValueDouble); + assertInstanceOf(V8ValueDouble.class, key); assertEquals("2147483648", key.toString()); })); } @@ -336,6 +338,50 @@ public void testGetSetDeletePublic() throws JavetException { assertTrue(v8ValueObject.delete("b")); V8Value v8Value = v8ValueObject.getUndefined("b"); assertNotNull(v8Value); + v8ValueObject.setString("d", "1"); + assertEquals("1", v8ValueObject.getString("d")); + assertTrue(v8ValueObject.has("d")); + v8ValueObject.setString("d", null); + assertNull(v8ValueObject.getString("d")); + assertTrue(v8ValueObject.has("d")); + Object[] keysAndValues = new Object[]{"x", 1, "y", 2, "z", 3}; + assertTrue(v8ValueObject.set(keysAndValues)); + for (int i = 0; i < keysAndValues.length / 2; i += 2) { + assertTrue(v8ValueObject.has(keysAndValues[i * 2])); + assertEquals(keysAndValues[i * 2 + 1], v8ValueObject.getInteger(keysAndValues[i * 2])); + } + } + String key = "a"; + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + for (Boolean value : new Boolean[]{true, false, null}) { + assertTrue(v8ValueObject.setBoolean(key, value)); + assertTrue(v8ValueObject.has(key)); + assertEquals(value, v8ValueObject.getBoolean(key)); + } + } + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + for (Double value : new Double[]{0.1D, 1.234D, -1.234D, Double.MIN_VALUE, Double.MAX_VALUE}) { + assertTrue(v8ValueObject.setDouble(key, value)); + assertTrue(v8ValueObject.has(key)); + assertEquals(value, v8ValueObject.getDouble(key), 0.001D); + } + assertTrue(v8ValueObject.setDouble(key, null)); + assertTrue(v8ValueObject.has(key)); + assertNull(v8ValueObject.getDouble(key)); + } + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + for (Integer value : new Integer[]{0, 1, -1, Integer.MIN_VALUE, Integer.MAX_VALUE, null}) { + assertTrue(v8ValueObject.setInteger(key, value)); + assertTrue(v8ValueObject.has(key)); + assertEquals(value, v8ValueObject.getInteger(key)); + } + } + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + for (Long value : new Long[]{0L, 1L, -1L, Long.MIN_VALUE, Long.MAX_VALUE, null}) { + assertTrue(v8ValueObject.setLong(key, value)); + assertTrue(v8ValueObject.has(key)); + assertEquals(value, v8ValueObject.getLong(key)); + } } v8Runtime.getExecutor("var test = { get a(){return b;}};").executeVoid(); try { @@ -402,6 +448,49 @@ public void testNestedObject() throws JavetException { } } + @Test + @Tag("performance") + public void testPerformanceSet() throws JavetException { + final int pairCount = 1000; + final int iterations = 1000; + // Test set one by one. + { + final long startTime = System.currentTimeMillis(); + int successCount = 0; + for (int i = 0; i < iterations; i++) { + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + for (int j = 0; j < pairCount; j++) { + if (v8ValueObject.set("a", "a")) { + successCount++; + } + } + } + } + final long stopTime = System.currentTimeMillis(); + final long tps = pairCount * iterations * 1000 / (stopTime - startTime); + logger.logInfo("Object set one by one: {0} tps.", tps); + assertEquals(pairCount * iterations, successCount); + } + // Test set by batch. + { + final long startTime = System.currentTimeMillis(); + int successCount = 0; + Object[] items = new Object[pairCount * 2]; + Arrays.fill(items, "a"); + for (int i = 0; i < iterations; i++) { + try (V8ValueObject v8ValueObject = v8Runtime.createV8ValueObject()) { + if (v8ValueObject.set(items)) { + successCount++; + } + } + } + final long stopTime = System.currentTimeMillis(); + final long tps = pairCount * iterations * 1000 / (stopTime - startTime); + logger.logInfo("Object set in a batch: {0} tps.", tps); + assertEquals(iterations, successCount); + } + } + @Test public void testPrototype() throws JavetException { v8Runtime.getExecutor("function A() {}; A.prototype.b = () => 2;").executeVoid(); diff --git a/src/test/java/com/caoccao/javet/values/reference/TestV8ValuePromise.java b/src/test/java/com/caoccao/javet/values/reference/TestV8ValuePromise.java index 483d7567e..d3ad9591a 100644 --- a/src/test/java/com/caoccao/javet/values/reference/TestV8ValuePromise.java +++ b/src/test/java/com/caoccao/javet/values/reference/TestV8ValuePromise.java @@ -77,7 +77,9 @@ public V8ValuePromise next() throws JavetException { } }; JavetCallbackContext javetCallbackContext = new JavetCallbackContext( - anonymous, anonymous.getClass().getMethod("get")); + "get", + anonymous, + anonymous.getClass().getMethod("get")); return v8Runtime.createV8ValueFunction(javetCallbackContext); } }); @@ -136,14 +138,14 @@ public void onCatch(V8Value v8Value) { @Override public void onFulfilled(V8Value v8Value) { - assertTrue(v8Value instanceof V8ValueInteger); + assertInstanceOf(V8ValueInteger.class, v8Value); assertEquals(1, ((V8ValueInteger) v8Value).getValue()); onFulfilledCalled = true; } @Override public void onRejected(V8Value v8Value) { - assertTrue(v8Value instanceof V8ValueInteger); + assertInstanceOf(V8ValueInteger.class, v8Value); assertEquals(2, ((V8ValueInteger) v8Value).getValue()); onRejectedCalled = true; } @@ -209,7 +211,7 @@ public void testFulfilled() throws JavetException { } @Test - public void testNoHandler() throws JavetException, NoSuchMethodException { + public void testNoHandler() throws JavetException { List events = new ArrayList<>(); IJavetPromiseRejectCallback callback = (event, promise, value) -> events.add(event); if (v8Host.getJSRuntimeType().isNode()) { diff --git a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueProxy.java b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueProxy.java index a51b5c272..e9ebcc555 100644 --- a/src/test/java/com/caoccao/javet/values/reference/TestV8ValueProxy.java +++ b/src/test/java/com/caoccao/javet/values/reference/TestV8ValueProxy.java @@ -19,8 +19,8 @@ import com.caoccao.javet.BaseTestJavetRuntime; import com.caoccao.javet.exceptions.JavetException; import com.caoccao.javet.exceptions.JavetExecutionException; -import com.caoccao.javet.interop.proxy.JavetDynamicProxyClassHandler; -import com.caoccao.javet.interop.proxy.JavetDynamicProxyObjectHandler; +import com.caoccao.javet.interop.proxy.JavetReflectionProxyClassHandler; +import com.caoccao.javet.interop.proxy.JavetReflectionProxyObjectHandler; import com.caoccao.javet.mock.MockPojo; import com.caoccao.javet.mock.MockPojoWithGenericGetterAndSetter; import org.junit.jupiter.api.Test; @@ -31,9 +31,79 @@ public class TestV8ValueProxy extends BaseTestJavetRuntime { @Test - public void testDynamicProxyHandlerInInstanceMode() throws JavetException { - JavetDynamicProxyObjectHandler handler = - new JavetDynamicProxyObjectHandler<>(v8Runtime, null, new MockPojo()); + public void testEmptyHandler() throws JavetException { + try (V8ValueObject v8ValueObject = v8Runtime.getExecutor("const x = {a:1,b:2}; x;").execute()) { + try (V8ValueProxy v8ValueProxy = v8Runtime.createV8ValueProxy(v8ValueObject)) { + assertNotNull(v8ValueProxy); + assertFalse(v8ValueProxy.isRevoked()); + assertEquals(1, v8ValueProxy.getInteger("a")); + assertEquals(2, v8ValueProxy.getInteger("b")); + assertTrue(v8ValueProxy.get("c").isUndefined()); + v8ValueObject.set("c", 3); + assertEquals(3, v8ValueProxy.getInteger("c")); + assertEquals("{\"a\":1,\"b\":2,\"c\":3}", v8ValueProxy.toJsonString()); + v8ValueProxy.revoke(); + assertTrue(v8ValueProxy.isRevoked()); + } + } + } + + @Test + public void testEmptyTargetAndEmptyHandler() throws JavetException { + try (V8ValueProxy v8ValueProxy = v8Runtime.createV8ValueProxy()) { + assertNotNull(v8ValueProxy); + assertFalse(v8ValueProxy.isRevoked()); + try (IV8ValueObject iV8ValueObject = v8ValueProxy.getTarget()) { + try (IV8ValueArray iV8ValueArray = iV8ValueObject.getOwnPropertyNames()) { + assertEquals(0, iV8ValueArray.getLength()); + } + iV8ValueObject.set("a", 1); + } + assertEquals("{\"a\":1}", v8ValueProxy.toJsonString()); + } + } + + @Test + public void testHandlerGet() throws JavetException { + try (V8ValueObject v8ValueObject = v8Runtime.getExecutor("var x = {a:1,b:2}; x;").execute()) { + try (V8ValueProxy v8ValueProxy = v8Runtime.createV8ValueProxy(v8ValueObject)) { + assertNotNull(v8ValueProxy); + assertFalse(v8ValueProxy.isRevoked()); + try (IV8ValueObject iV8ValueObjectHandler = v8ValueProxy.getHandler()) { + iV8ValueObjectHandler.bindFunction("get", "(target, prop, receiver) => {" + + " if (prop in target) {" + + " return target[prop] + 1;" + + " }" + + " return undefined;" + + "};"); + } + assertEquals(2, v8ValueProxy.getInteger("a")); + assertEquals(3, v8ValueProxy.getInteger("b")); + v8ValueProxy.revoke(); + assertTrue(v8ValueProxy.isRevoked()); + try { + v8ValueProxy.get("a"); + fail("Failed to report TypeError."); + } catch (JavetExecutionException e) { + assertEquals("TypeError: Cannot perform 'get' on a proxy that has been revoked", e.getMessage()); + } + } + } + } + + @Test + public void testNativeProxyCreation() throws JavetException { + try (V8ValueProxy v8ValueProxy = v8Runtime.getExecutor( + "const b = {}; const a = new Proxy(RegExp, b); a;").execute()) { + assertNotNull(v8ValueProxy); + assertFalse(v8ValueProxy.isRevoked()); + } + } + + @Test + public void testReflectionProxyHandlerInInstanceMode() throws JavetException { + JavetReflectionProxyObjectHandler handler = + new JavetReflectionProxyObjectHandler<>(v8Runtime, null, new MockPojo()); try (V8ValueObject v8ValueObject = v8Runtime.getExecutor("const x = {a:1,b:2}; x;").execute()) { try (V8ValueProxy v8ValueProxy = v8Runtime.createV8ValueProxy(v8ValueObject)) { assertNotNull(v8ValueProxy); @@ -109,9 +179,9 @@ public void testDynamicProxyHandlerInInstanceMode() throws JavetException { } @Test - public void testDynamicProxyHandlerInStaticMode() throws JavetException { - JavetDynamicProxyClassHandler> handler = - new JavetDynamicProxyClassHandler<>(v8Runtime, null, MockPojo.class); + public void testReflectionProxyHandlerInStaticMode() throws JavetException { + JavetReflectionProxyClassHandler, ?> handler = + new JavetReflectionProxyClassHandler<>(v8Runtime, null, MockPojo.class); assertEquals(MockPojo.class, handler.getTargetObject()); try (V8ValueObject v8ValueObject = v8Runtime.getExecutor("const x = {a:1,b:2}; x;").execute()) { try (V8ValueProxy v8ValueProxy = v8Runtime.createV8ValueProxy(v8ValueObject)) { @@ -153,9 +223,9 @@ public void testDynamicProxyHandlerInStaticMode() throws JavetException { } @Test - public void testDynamicProxyHandlerWithGenericGetterAndSetter() throws JavetException { - JavetDynamicProxyObjectHandler handler = - new JavetDynamicProxyObjectHandler<>(v8Runtime, null, new MockPojoWithGenericGetterAndSetter()); + public void testReflectionProxyHandlerWithGenericGetterAndSetter() throws JavetException { + JavetReflectionProxyObjectHandler handler = + new JavetReflectionProxyObjectHandler<>(v8Runtime, null, new MockPojoWithGenericGetterAndSetter()); handler.getTargetObject().set("c", "3"); handler.getTargetObject().set("d", "4"); try (V8ValueObject v8ValueObject = v8Runtime.getExecutor("const x = {a:1,b:2}; x;").execute()) { @@ -192,74 +262,4 @@ public void testDynamicProxyHandlerWithGenericGetterAndSetter() throws JavetExce v8Runtime.lowMemoryNotification(); } } - - @Test - public void testEmptyHandler() throws JavetException { - try (V8ValueObject v8ValueObject = v8Runtime.getExecutor("const x = {a:1,b:2}; x;").execute()) { - try (V8ValueProxy v8ValueProxy = v8Runtime.createV8ValueProxy(v8ValueObject)) { - assertNotNull(v8ValueProxy); - assertFalse(v8ValueProxy.isRevoked()); - assertEquals(1, v8ValueProxy.getInteger("a")); - assertEquals(2, v8ValueProxy.getInteger("b")); - assertTrue(v8ValueProxy.get("c").isUndefined()); - v8ValueObject.set("c", 3); - assertEquals(3, v8ValueProxy.getInteger("c")); - assertEquals("{\"a\":1,\"b\":2,\"c\":3}", v8ValueProxy.toJsonString()); - v8ValueProxy.revoke(); - assertTrue(v8ValueProxy.isRevoked()); - } - } - } - - @Test - public void testEmptyTargetAndEmptyHandler() throws JavetException { - try (V8ValueProxy v8ValueProxy = v8Runtime.createV8ValueProxy()) { - assertNotNull(v8ValueProxy); - assertFalse(v8ValueProxy.isRevoked()); - try (IV8ValueObject iV8ValueObject = v8ValueProxy.getTarget()) { - try (IV8ValueArray iV8ValueArray = iV8ValueObject.getOwnPropertyNames()) { - assertEquals(0, iV8ValueArray.getLength()); - } - iV8ValueObject.set("a", 1); - } - assertEquals("{\"a\":1}", v8ValueProxy.toJsonString()); - } - } - - @Test - public void testHandlerGet() throws JavetException { - try (V8ValueObject v8ValueObject = v8Runtime.getExecutor("var x = {a:1,b:2}; x;").execute()) { - try (V8ValueProxy v8ValueProxy = v8Runtime.createV8ValueProxy(v8ValueObject)) { - assertNotNull(v8ValueProxy); - assertFalse(v8ValueProxy.isRevoked()); - try (IV8ValueObject iV8ValueObjectHandler = v8ValueProxy.getHandler()) { - iV8ValueObjectHandler.bindFunction("get", "(target, prop, receiver) => {" + - " if (prop in target) {" + - " return target[prop] + 1;" + - " }" + - " return undefined;" + - "};"); - } - assertEquals(2, v8ValueProxy.getInteger("a")); - assertEquals(3, v8ValueProxy.getInteger("b")); - v8ValueProxy.revoke(); - assertTrue(v8ValueProxy.isRevoked()); - try { - v8ValueProxy.get("a"); - fail("Failed to report TypeError."); - } catch (JavetExecutionException e) { - assertEquals("TypeError: Cannot perform 'get' on a proxy that has been revoked", e.getMessage()); - } - } - } - } - - @Test - public void testNativeProxyCreation() throws JavetException { - try (V8ValueProxy v8ValueProxy = v8Runtime.getExecutor( - "const b = {}; const a = new Proxy(RegExp, b); a;").execute()) { - assertNotNull(v8ValueProxy); - assertFalse(v8ValueProxy.isRevoked()); - } - } }