美文网首页
编译 JavaScript 引擎 QuickJS 到 Andro

编译 JavaScript 引擎 QuickJS 到 Andro

作者: ImWiki | 来源:发表于2021-05-23 21:11 被阅读0次

    QuickJS 是一个小型并且可嵌入的 Javascript 引擎,它支持ES2020规范,包括模块,异步生成器和代理器。编译下来只有几百KB,相比 V8 需要几MB小得多,在对大小有要求的嵌入式设备来说是 V8 一个不错的替代品。国人写了一份中文文档可以参考。

    在Mac OS编译QuickJS

    # 下载代码
    git clone https://github.com/bellard/quickjs
    cd quickjs
    # 编译
    make
    

    执行完 make 后,就会在根目录生成了qjs可执行文件,就可以进行测试

    ./qjs examples/hello.js
    

    对象介绍

    • JSRuntime:JavaScript 的运行时,可以创建多个运行时,但是不同的运行时不能共享对象。
    • JSContext:一个 JSRuntime 可以创建多个 JSContext,同一个 JSRuntime 下的 JSContext 可以共享对象。
    • JSValue:JavaScript 的变量及 Function 等。

    在Android编译QuickJS

    创建JNI项目

    这一步就不介绍了,自行使用Android Studio创建一个JNI的项目。

    由于QuickJS使用了一些高版本的API,所以 minSdkVersion 必须大于18。

    把QuickJS代码放到项目中

    需要把QuickJS 的代码下载到main/cpp/quickjs。
    文件结构如下:

    main
    ├── AndroidManifest.xml
    ├── cpp
    │   ├── CMakeLists.txt
    │   ├── quickjs-jni.cpp
    │   └── quickjs
    │       ├── CMakeLists.txt
    │       └── quickjs
    │           ├── VERSION
    │           ├── cutils.c
    │           ├── cutils.h
    │           ├── libbf.c
    │           ├── libbf.h
    │           ├── libregexp.c
    │           ├── libregexp.h
    │           ├── libunicode.c
    │           ├── libunicode.h
    │           ├── quickjs.c
    │           └── quickjs.h
    └── java
        └── com/quickjs/android/QuickJS.java
    

    在 quickjs 目录下创建一个CMakeLists.txt文件,文件内容如下:

    cmake_minimum_required(VERSION 3.10.2)
    project(quickjs CXX)
    include_directories(quickjs)
    set(SOURCE_DIR
            quickjs/cutils.c
            quickjs/libbf.c
            quickjs/libregexp.c
            quickjs/libunicode.c
            quickjs/quickjs.c
            )
    
    file(STRINGS "quickjs/VERSION" CONFIG_VERSION)
    add_definitions(-DCONFIG_VERSION="${CONFIG_VERSION}")
    add_definitions(-DCONFIG_BIGNUM)
    add_definitions(-D_GNU_SOURCE)
    add_definitions(-DCONFIG_CC="gcc")
    add_definitions(-DCONFIG_PREFIX="/usr/local")
    add_library(
            ${PROJECT_NAME}
            SHARED
            ${SOURCE_DIR}
    )
    target_include_directories(${PROJECT_NAME} PUBLIC .)
    

    把cpp/CMakeLists.txt修改成

    cmake_minimum_required(VERSION 3.10.2)
    project("quickjs-android")
    add_subdirectory(./quickjs)
    add_library(
            ${PROJECT_NAME}
            SHARED
            quickjs-jni.cpp)
    find_library(
            log-lib
            log)
    target_link_libraries(
            ${PROJECT_NAME}
            ${log-lib}
            quickjs
    )
    

    QuickJS.java内容如下:

    package com.quickjs.android;
    
    public class QuickJS {
        public static native int executeIntegerScript(String source,String fileName);
    }
    

    quickjs-jni.cpp 内容如下:

    #include <jni.h>
    #include <string>
    #include <quickjs/quickjs.h>
    
    
    extern "C"
    JNIEXPORT jint JNICALL
    Java_com_quickjs_android_QuickJS_executeIntegerScript(JNIEnv *env, jclass clazz, jstring jCode,
                                                          jstring jFileName) {
        JSRuntime *jsRuntime = JS_NewRuntime();
        JSContext *context = JS_NewContext(jsRuntime);
        const char *code = env->GetStringUTFChars(jCode, NULL);
        const int code_length = env->GetStringUTFLength(jCode);
        const char *file_name = env->GetStringUTFChars(jFileName, NULL);
        int flags = 0;
        JSValue val = JS_Eval(context, code, (size_t) code_length, file_name, flags);
        int result = JS_VALUE_GET_INT(val);
        return result;
    }
    
    测试
        protected void test() {
            int result = QuickJS.executeIntegerScript("var a = 2+2;\n a;", "file.js");
            Log.e("quickjs", String.valueOf(result));
        }
    
        static {
            System.loadLibrary("quickjs");
            System.loadLibrary("quickjs-android");
        }
    

    就会输出结果:4

    项目代码

    https://github.com/taoweiji/quickjs-android

    总结

    编译下来armeabi-v7a的so文件仅仅380KB,相比Google V8引擎的7MB小得多。上面只是简单的示例,需要完整使用 QuickJS 功能还需要大量的适配工作,推荐使用 quickjs-android

    相关文章

      网友评论

          本文标题:编译 JavaScript 引擎 QuickJS 到 Andro

          本文链接:https://www.haomeiwen.com/subject/bfjajltx.html