diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index a204de1..6be63bd 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -19,7 +19,14 @@ jobs: timeout-minutes: 60 strategy: matrix: - os: [macos-latest, windows-latest, ubuntu-latest] + os: + [ + macos-latest, + macos-13, + windows-latest, + ubuntu-latest, + ubuntu-24.04-arm, + ] steps: - name: Clone repository @@ -33,10 +40,22 @@ jobs: deno-version: v2.x - name: install webkit2gtk (Linux) - if: matrix.os == 'ubuntu-latest' + if: startsWith(matrix.os, 'ubuntu') run: | sudo apt-get update - sudo apt-get install -y webkit2gtk-4.0 + sudo apt-get install -y webkitgtk-6.0 libwebkitgtk-6.0-dev cmake ninja-build clang pkg-config libgtk-4-dev + + - name: Install ninja (macOS) + if: startsWith(matrix.os, 'macos') + run: | + brew install ninja + brew install llvm + echo "WEBVIEW_CLANG_FORMAT_EXE=$(brew --prefix llvm)/bin/clang-format" >> $GITHUB_ENV + + - name: Install ninja (Windows) + if: matrix.os == 'windows-latest' + run: | + choco install ninja - name: Build dynamic library run: deno task build @@ -50,15 +69,17 @@ jobs: build/*.dylib build/*.so -# - name: Release Plugin -# uses: softprops/action-gh-release@master -# env: -# GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} -# with: -# tag_name: "webview_deno release" -# draft: true -# files: | -# build/libwebview.x86_64.dylib -# build/libwebview.so -# build/webview.dll -# build/Webview2Loader.dll + # - name: Release Plugin + # uses: softprops/action-gh-release@master + # env: + # GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + # with: + # tag_name: "webview_deno release" + # draft: true + # files: | + # build/libwebview.x86_64.dylib + # build/libwebview.aarch64.dylib + # build/libwebview.x86_64.so + # build/libwebview.aarch64.so + # build/webview.dll + # build/Webview2Loader.dll diff --git a/script/build.bat b/script/build.bat index 103aeed..afef04e 100644 --- a/script/build.bat +++ b/script/build.bat @@ -1,76 +1,29 @@ @echo off - -echo Prepare directories... -set script_dir=%~dp0 -set src_dir=%script_dir%..\webview -set build_dir=%script_dir%..\build -mkdir "%build_dir%" - -echo Webview directory: %src_dir% -echo Build directory: %build_dir% - -:: If you update the nuget package, change its version here -set nuget_version=1.0.1150.38 -echo Using Nuget Package microsoft.web.webview2.%nuget_version% -if not exist "%script_dir%\microsoft.web.webview2.%nuget_version%" ( - curl -sSLO https://dist.nuget.org/win-x86-commandline/latest/nuget.exe - nuget.exe install Microsoft.Web.Webview2 -Version %nuget_version% -OutputDirectory %script_dir% - echo Nuget package installed -) - echo Looking for vswhere.exe... set "vswhere=%ProgramFiles(x86)%\Microsoft Visual Studio\Installer\vswhere.exe" if not exist "%vswhere%" set "vswhere=%ProgramFiles%\Microsoft Visual Studio\Installer\vswhere.exe" if not exist "%vswhere%" ( - echo ERROR: Failed to find vswhere.exe - exit /b 1 + echo ERROR: Failed to find vswhere.exe + exit /b 1 ) echo Found %vswhere% echo Looking for VC... for /f "usebackq tokens=*" %%i in (`"%vswhere%" -latest -products * -requires Microsoft.VisualStudio.Component.VC.Tools.x86.x64 -property installationPath`) do ( - set vc_dir=%%i + set vc_dir=%%i ) if not exist "%vc_dir%\Common7\Tools\vsdevcmd.bat" ( - echo ERROR: Failed to find VC tools x86/x64 - exit /b 1 + echo ERROR: Failed to find VC tools x86/x64 + exit /b 1 ) echo Found %vc_dir% -:: 4100: unreferenced formal parameter -set warning_params=/W4 /wd4100 - -:: build dlls if not found -if not exist "%src_dir%\dll\x64\webview.dll" ( - mkdir "%src_dir%\dll\x86" - mkdir "%src_dir%\dll\x64" - copy "%script_dir%\microsoft.web.webview2.%nuget_version%\build\native\x64\WebView2Loader.dll" "%src_dir%\dll\x64" - copy "%script_dir%\microsoft.web.webview2.%nuget_version%\build\native\x86\WebView2Loader.dll" "%src_dir%\dll\x86" - - call "%vc_dir%\Common7\Tools\vsdevcmd.bat" -arch=x86 -host_arch=x64 - - echo "Building webview.dll (x86)" - cl %warning_params% ^ - /D "WEBVIEW_API=__declspec(dllexport)" ^ - /I "%script_dir%\microsoft.web.webview2.%nuget_version%\build\native\include" ^ - "%script_dir%\microsoft.web.webview2.%nuget_version%\build\native\x86\WebView2Loader.dll.lib" ^ - /std:c++17 /EHsc "/Fo%build_dir%"\ ^ - "%src_dir%\webview.cc" /link /DLL "/OUT:%src_dir%\dll\x86\webview.dll" || exit \b +call "%vc_dir%\Common7\Tools\vsdevcmd.bat" -arch=x64 -host_arch=x64 +cd %~dp0..\webview - call "%vc_dir%\Common7\Tools\vsdevcmd.bat" -arch=x64 -host_arch=x64 - echo "Building webview.dll (x64)" - cl %warning_params% ^ - /D "WEBVIEW_API=__declspec(dllexport)" ^ - /I "%script_dir%\microsoft.web.webview2.%nuget_version%\build\native\include" ^ - "%script_dir%\microsoft.web.webview2.%nuget_version%\build\native\x64\WebView2Loader.dll.lib" ^ - /std:c++17 /EHsc "/Fo%build_dir%"\ ^ - "%src_dir%\webview.cc" /link /DLL "/OUT:%src_dir%\dll\x64\webview.dll" || exit \b -) -if not exist "%build_dir%\webview.dll" ( - copy "%src_dir%\dll\x64\webview.dll" %build_dir% -) -if not exist "%build_dir%\WebView2Loader.dll" ( - copy "%script_dir%\microsoft.web.webview2.%nuget_version%\build\native\x64\WebView2Loader.dll" "%build_dir%" -) +cmake -G "Ninja Multi-Config" -B build -S . ^ + -DWEBVIEW_BUILD_DOCS=OFF ^ + -DWEBVIEW_USE_CLANG_TIDY=OFF ^ + -DWEBVIEW_USE_CLANG_FORMAT=OFF -call "%vc_dir%\Common7\Tools\vsdevcmd.bat" -arch=x64 -host_arch=x64 +cmake --build build --config Release diff --git a/script/build.ts b/script/build.ts index 85b8205..e15b209 100644 --- a/script/build.ts +++ b/script/build.ts @@ -1,162 +1,38 @@ -import { ensureDir } from "jsr:@std/fs@0.218/ensure_dir"; +import { $ } from "jsr:@david/dax@0.42.0"; -const decoder = new TextDecoder(); -const architectures = [["x86_64", "x86_64"], ["aarch64", "arm64"]] as const; +const { os } = Deno.build; +$.setPrintCommand(true); -const ExitType = { - Exit: "exit", - Fail: "fail", - Never: "never", -} as const; -type ExitType = typeof ExitType[keyof typeof ExitType]; - -const LogType = { - Success: "success", - Always: "always", - Fail: "fail", - Never: "never", -} as const; -type LogType = typeof LogType[keyof typeof LogType]; - -function indent(source: string, spaces = 2): string { - return source.split("\n").map((line) => `${" ".repeat(spaces)}${line}\n`) - .join(""); -} - -async function command( - cmd: string, - { opts, exit, log }: { opts?: T; exit?: ExitType; log?: LogType } = {}, -): Promise<{ - code: number; - stdout: string; - stderr: string; -}> { - if (opts !== undefined) { - opts.stdout = "piped"; - opts.stderr = "piped"; - } - - exit ??= ExitType.Never; - log ??= LogType.Always; - - const command = new Deno.Command(cmd, opts); - const { code, stdout, stderr } = await command.output(); - - const stdoutStr = decoder.decode(stdout); - const stderrStr = decoder.decode(stderr); - - if (code === 0) { - if (log !== "never") { - console.log(`Successfully ran "${cmd} ${(opts?.args ?? []).join(" ")}"`); - } - - if (log === "success" || log === "always") { - if (stdoutStr.length !== 0) { - console.log(`stdout:\n${indent(stdoutStr)}`); - } - if (stderrStr.length !== 0) { - console.log(`stderr:\n${indent(stderrStr)}`); - } - } - } else { - if (log !== "never") { - console.log(`Failed run "${cmd}"`); - } - - if (log === "fail" || log === "always") { - if (stdoutStr.length !== 0) { - console.log(`stdout:\n${indent(stdoutStr)}`); - } - if (stderrStr.length !== 0) { - console.log(`stderr:\n${indent(stderrStr)}`); - } - console.log(`code: ${code}`); - } - - if (exit === ExitType.Fail) { - Deno.exit(code); - } - } - - if (exit === ExitType.Exit) { - Deno.exit(code); - } - - return { - code, - stdout: stdoutStr, - stderr: stderrStr, - }; -} - -await ensureDir("build"); - -switch (Deno.build.os) { - case "windows": { - await command("script/build.bat", { - exit: ExitType.Exit, - }); +await $.path("./build").ensureDir(); +switch (os) { + case "windows": + await $`script/build.bat`; + await $`cp webview/build/core/Release/webview.dll build/webview.dll`; break; - } - - case "darwin": { - for (const [denoArch, gccArch] of architectures) { - await command("c++", { - opts: { - exit: ExitType.Fail, - args: [ - "webview/webview.cc", - "-dynamiclib", - "-fpic", - "-DWEBVIEW_COCOA", - "-std=c++11", - "-Wall", - "-Wextra", - "-pedantic", - "-framework", - "WebKit", - "-arch", - gccArch, - "-o", - `build/libwebview.${denoArch}.dylib`, - ], - }, - }); - } - Deno.exit(0); + case "linux": + $.cd("webview"); + await $`export PATH=/usr/lib/llvm14/bin/:/usr/lib/llvm-14/bin/:/usr/lib64/llvm15/bin/:$PATH`; + await $`cmake -G Ninja -B build -S . -D CMAKE_BUILD_TYPE=Release -D WEBVIEW_WEBKITGTK_API=6.0 -DWEBVIEW_ENABLE_CHECKS=false -DCMAKE_TOOLCHAIN_FILE=cmake/toolchains/host-llvm.cmake -DWEBVIEW_USE_CLANG_TIDY=OFF -DWEBVIEW_BUILD_DOCS=OFF -DWEBVIEW_USE_CLANG_FORMAT=OFF`; + await $`cmake --build build`; + await $`cp build/core/libwebview.so ../build/libwebview.${Deno.build.arch}.so`; + await $`strip ../build/libwebview.${Deno.build.arch}.so`; break; - } - - case "linux": { - const { stdout } = await command("pkg-config", { - opts: { - args: [ - "--cflags", - "--libs", - "gtk+-3.0", - "webkit2gtk-4.0", - ], - }, - }); - await command("c++", { - opts: { - exit: ExitType.Fail, - args: [ - "webview/webview.cc", - "-DWEBVIEW_GTK", - "-shared", - "-std=c++11", - "-Wall", - "-Wextra", - "-pedantic", - "-fpic", - ...stdout.trim().split(" "), - "-o", - "build/libwebview.so", - ], - }, - }); - Deno.exit(0); + case "darwin": + $.cd("webview"); + await $`cmake -G "Ninja Multi-Config" -B build -S . \ + -DCMAKE_BUILD_TYPE=Release \ + -DWEBVIEW_BUILD_TESTS=OFF \ + -DWEBVIEW_BUILD_EXAMPLES=OFF \ + -DWEBVIEW_USE_CLANG_TOOLS=OFF \ + -DWEBVIEW_ENABLE_CHECKS=OFF \ + -DWEBVIEW_USE_CLANG_TIDY=OFF \ + -DWEBVIEW_BUILD_DOCS=OFF \ + -DWEBVIEW_USE_CLANG_FORMAT=OFF \ + -DWEBVIEW_CLANG_FORMAT_EXE=${Deno.env.get( + "WEBVIEW_CLANG_FORMAT_EXE", + )!}`; + await $`cmake --build build --config Release`; + await $`cp build/core/Release/libwebview.dylib ../build/libwebview.${Deno.build.arch}.dylib`; + await $`strip -x -S ../build/libwebview.${Deno.build.arch}.dylib`; break; - } } diff --git a/src/ffi.ts b/src/ffi.ts index fff7bae..58dbb11 100644 --- a/src/ffi.ts +++ b/src/ffi.ts @@ -105,6 +105,7 @@ export const lib = await dlopen( url, cache, suffixes: { + linux: `.${Deno.build.arch}`, darwin: `.${Deno.build.arch}`, }, }, diff --git a/webview b/webview index 2ee04cc..c5b1940 160000 --- a/webview +++ b/webview @@ -1 +1 @@ -Subproject commit 2ee04ccd0530e3928a872f5d508c114403803e61 +Subproject commit c5b19403382ef089f9933ea5331c76aa35414589