react-native-executorch 0.10.0 → 0.10.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/android/build.gradle.kts
CHANGED
|
@@ -53,6 +53,44 @@ fun rneBuildConfig(): Map<*, *> {
|
|
|
53
53
|
val rneConfig = rneBuildConfig()
|
|
54
54
|
fun rneFlag(key: String): String = if (rneConfig[key] != false) "ON" else "OFF"
|
|
55
55
|
|
|
56
|
+
/**
|
|
57
|
+
* The prebuilt ExecuTorch runtime is not in the npm tarball - `package.json`
|
|
58
|
+
* excludes it and `scripts/download-libs.js` fetches it from the matching
|
|
59
|
+
* GitHub release in a postinstall hook. When a package manager skips that hook
|
|
60
|
+
* the install still looks clean and the failure surfaces much later, out of
|
|
61
|
+
* CMake, blamed on a missing library rather than on the install. Fail here with
|
|
62
|
+
* the fix instead.
|
|
63
|
+
*/
|
|
64
|
+
fun requireNativeArtifacts() {
|
|
65
|
+
val libsDir = file("../third-party/android/libs/executorch")
|
|
66
|
+
val present = libsDir.listFiles()
|
|
67
|
+
?.filter { it.isDirectory && it.resolve("libexecutorch.so").exists() }
|
|
68
|
+
.orEmpty()
|
|
69
|
+
if (present.isNotEmpty()) return
|
|
70
|
+
|
|
71
|
+
throw GradleException(
|
|
72
|
+
"""
|
|
73
|
+
react-native-executorch is missing its native artifacts:
|
|
74
|
+
|
|
75
|
+
${libsDir.absolutePath}
|
|
76
|
+
|
|
77
|
+
They are downloaded by this package's postinstall hook, which your
|
|
78
|
+
package manager did not run. pnpm 10 and later block dependency build
|
|
79
|
+
scripts by default ("Ignored build scripts"), and so do
|
|
80
|
+
`--ignore-scripts` and `npm ci --ignore-scripts`. Re-run the hook:
|
|
81
|
+
|
|
82
|
+
pnpm approve-builds react-native-executorch # pnpm
|
|
83
|
+
npm rebuild react-native-executorch # npm
|
|
84
|
+
node node_modules/react-native-executorch/scripts/download-libs.js
|
|
85
|
+
|
|
86
|
+
If you provision the libraries yourself, put them under
|
|
87
|
+
third-party/android/libs/executorch/<abi>/ before building.
|
|
88
|
+
""".trimIndent()
|
|
89
|
+
)
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
requireNativeArtifacts()
|
|
93
|
+
|
|
56
94
|
/**
|
|
57
95
|
* ExecuTorch only supports these ABIs. Honor the app's `reactNativeArchitectures`
|
|
58
96
|
* (e.g. Expo passes `-PreactNativeArchitectures=arm64-v8a` for device builds) so
|
|
@@ -70,7 +108,12 @@ android {
|
|
|
70
108
|
compileSdk = (getExtOrDefault("compileSdkVersion", 34) as Number).toInt()
|
|
71
109
|
|
|
72
110
|
defaultConfig {
|
|
73
|
-
|
|
111
|
+
// The prebuilt ExecuTorch runtime is compiled against Android API 26 -
|
|
112
|
+
// `.note.android.ident` in libexecutorch.so, libxnnpack_executorch_backend.so
|
|
113
|
+
// and libvulkan_executorch_backend.so all read 26 - so an app below that
|
|
114
|
+
// ships a library its linker is not guaranteed to be able to load. The
|
|
115
|
+
// default was 21, which let such a build through to fail on the device.
|
|
116
|
+
minSdk = (getExtOrDefault("minSdkVersion", 26) as Number).toInt()
|
|
74
117
|
targetSdk = (getExtOrDefault("targetSdkVersion", 34) as Number).toInt()
|
|
75
118
|
consumerProguardFiles("consumer-proguard-rules.pro")
|
|
76
119
|
|
|
@@ -12,7 +12,7 @@ const DOWNLOAD_EVENT_ENDPOINT = 'https://ai.swmansion.com/telemetry/downloads/ap
|
|
|
12
12
|
// self-referencing import would need package `exports` support in the consuming
|
|
13
13
|
// bundler to load at all. A wrong value here is analytics noise; a failed
|
|
14
14
|
// import would break the bundle.
|
|
15
|
-
const LIB_VERSION = '0.10.
|
|
15
|
+
const LIB_VERSION = '0.10.1';
|
|
16
16
|
|
|
17
17
|
// Anonymous analytics are on by default; apps opt out via setTelemetryEnabled.
|
|
18
18
|
let telemetryEnabled = true;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "react-native-executorch",
|
|
3
|
-
"version": "0.10.
|
|
3
|
+
"version": "0.10.1",
|
|
4
4
|
"nativeLibsVersion": "0.10.0",
|
|
5
5
|
"description": "An easy way to run AI models in React Native with ExecuTorch",
|
|
6
6
|
"main": "./lib/module/index.js",
|
|
@@ -142,7 +142,7 @@
|
|
|
142
142
|
"react": "*",
|
|
143
143
|
"react-native": "*",
|
|
144
144
|
"react-native-blob-util": "^0.24.0",
|
|
145
|
-
"react-native-worklets": "
|
|
145
|
+
"react-native-worklets": ">=0.10.0 <0.13.0"
|
|
146
146
|
},
|
|
147
147
|
"peerDependenciesMeta": {
|
|
148
148
|
"@kesha-antonov/react-native-background-downloader": {
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
require "fileutils"
|
|
1
2
|
require "json"
|
|
2
3
|
|
|
3
4
|
package = JSON.parse(File.read(File.join(__dir__, "package.json")))
|
|
@@ -6,19 +7,59 @@ package = JSON.parse(File.read(File.join(__dir__, "package.json")))
|
|
|
6
7
|
# Falls back to all features enabled if the file doesn't exist (e.g. a fresh
|
|
7
8
|
# checkout where the native libs were provisioned manually).
|
|
8
9
|
rne_build_config_path = File.join(__dir__, "rne-build-config.json")
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
10
|
+
rne_build_config =
|
|
11
|
+
File.exist?(rne_build_config_path) ? JSON.parse(File.read(rne_build_config_path)) : {}
|
|
12
|
+
|
|
13
|
+
# Every flag reads `!= false`, so an absent file and an absent key both mean
|
|
14
|
+
# enabled. Keep the hash rather than branching on the file: `opencvPod` below
|
|
15
|
+
# is read from it too, and a nil `rne_build_config` there is a NoMethodError.
|
|
16
|
+
enable_opencv = rne_build_config["enableOpencv"] != false
|
|
17
|
+
enable_phonemis = rne_build_config["enablePhonemis"] != false
|
|
18
|
+
enable_xnnpack = rne_build_config["enableXnnpack"] != false
|
|
19
|
+
enable_coreml = rne_build_config["enableCoreml"] != false
|
|
20
|
+
enable_mlx = rne_build_config["enableMlx"] != false
|
|
21
|
+
|
|
22
|
+
# The native artifacts are not in the npm tarball - `package.json` excludes
|
|
23
|
+
# them and `scripts/download-libs.js` fetches them from the matching GitHub
|
|
24
|
+
# release in a postinstall hook. When a package manager skips that hook the
|
|
25
|
+
# install still looks clean, and so does `pod install`: CocoaPods never checks
|
|
26
|
+
# that a vendored framework exists. The build then fails minutes later with
|
|
27
|
+
#
|
|
28
|
+
# error: Build input files cannot be found:
|
|
29
|
+
# '.../XnnpackBackend.xcframework/ios-arm64-simulator/libXnnpackBackend.a'
|
|
30
|
+
#
|
|
31
|
+
# which names neither the cause nor the fix. Fail here instead, while the user
|
|
32
|
+
# is still looking at the install that caused it.
|
|
33
|
+
required_artifacts = { "ExecutorchLib.xcframework" => true }
|
|
34
|
+
required_artifacts["XnnpackBackend.xcframework"] = enable_xnnpack
|
|
35
|
+
required_artifacts["CoreMLBackend.xcframework"] = enable_coreml
|
|
36
|
+
required_artifacts["MLXBackend.xcframework"] = enable_mlx
|
|
37
|
+
|
|
38
|
+
missing = required_artifacts
|
|
39
|
+
.select { |_, required| required }
|
|
40
|
+
.keys
|
|
41
|
+
.map { |name| File.join(__dir__, "third-party/ios", name) }
|
|
42
|
+
.reject { |path| File.directory?(path) }
|
|
43
|
+
|
|
44
|
+
unless missing.empty?
|
|
45
|
+
# Pod::Informative renders as a plain `[!]` message rather than a backtrace.
|
|
46
|
+
raise(defined?(Pod::Informative) ? Pod::Informative : StandardError, <<~MESSAGE)
|
|
47
|
+
react-native-executorch is missing its native artifacts:
|
|
48
|
+
|
|
49
|
+
#{missing.map { |path| " #{path}" }.join("\n")}
|
|
50
|
+
|
|
51
|
+
They are downloaded by this package's postinstall hook, which your package
|
|
52
|
+
manager did not run. pnpm 10 and later block dependency build scripts by
|
|
53
|
+
default ("Ignored build scripts"), and so do `--ignore-scripts` and
|
|
54
|
+
`npm ci --ignore-scripts`. Re-run the hook, then `pod install` again:
|
|
55
|
+
|
|
56
|
+
pnpm approve-builds react-native-executorch # pnpm
|
|
57
|
+
npm rebuild react-native-executorch # npm
|
|
58
|
+
node node_modules/react-native-executorch/scripts/download-libs.js
|
|
59
|
+
|
|
60
|
+
If you provision the libraries yourself, put them under
|
|
61
|
+
third-party/ios/ before installing pods.
|
|
62
|
+
MESSAGE
|
|
22
63
|
end
|
|
23
64
|
|
|
24
65
|
Pod::Spec.new do |s|
|
|
@@ -97,6 +138,34 @@ Pod::Spec.new do |s|
|
|
|
97
138
|
exclude_files += phonemis_source_files unless enable_phonemis
|
|
98
139
|
s.exclude_files = exclude_files
|
|
99
140
|
|
|
141
|
+
# --- Public headers ---
|
|
142
|
+
# `use_frameworks!` - set directly for Firebase, or through
|
|
143
|
+
# expo-build-properties' `useFrameworks: "static"` - makes CocoaPods build
|
|
144
|
+
# this pod as a framework, and Xcode's Headers build phase copies every
|
|
145
|
+
# *public* header into one flat `Headers/` directory. With no
|
|
146
|
+
# `public_header_files` every header in `source_files` is public, and the
|
|
147
|
+
# tree has 21 basenames that occur more than once (`Types.h` in eleven task
|
|
148
|
+
# directories, `constants.h` in thirteen phonemis ones), so the build fails
|
|
149
|
+
# at planning with `Multiple commands produce .../Headers/Types.h` before a
|
|
150
|
+
# single file compiles. See discussion #203.
|
|
151
|
+
#
|
|
152
|
+
# Only the Objective-C entry points have to be visible to the app. The C++
|
|
153
|
+
# headers are reached through the HEADER_SEARCH_PATHS below, so narrowing the
|
|
154
|
+
# public set costs nothing, and `__tests__/api/podspecPublicHeaders.test.ts`
|
|
155
|
+
# keeps it collision-free.
|
|
156
|
+
public_header_files = [
|
|
157
|
+
"ios/**/*.h",
|
|
158
|
+
]
|
|
159
|
+
# ==============================================================================
|
|
160
|
+
# LEGACY SUPPORT: include the legacy entry point
|
|
161
|
+
# (Remove when react-native-executorch/legacy is dropped)
|
|
162
|
+
# ==============================================================================
|
|
163
|
+
public_header_files += [
|
|
164
|
+
"legacy/ios/**/*.h",
|
|
165
|
+
]
|
|
166
|
+
# ==============================================================================
|
|
167
|
+
s.public_header_files = public_header_files
|
|
168
|
+
|
|
100
169
|
# --- Preprocessor flags ---
|
|
101
170
|
extra_compiler_flags = []
|
|
102
171
|
extra_compiler_flags << "-DRNE_ENABLE_OPENCV" if enable_opencv
|
|
@@ -143,6 +212,64 @@ Pod::Spec.new do |s|
|
|
|
143
212
|
'EXCLUDED_ARCHS[sdk=iphonesimulator*]' => 'x86_64',
|
|
144
213
|
}
|
|
145
214
|
|
|
215
|
+
# iOS OpenCV is provided by a CocoaPod (not a downloaded tarball), normally
|
|
216
|
+
# our own opencv-rne.
|
|
217
|
+
#
|
|
218
|
+
# An app can already carry OpenCV through another library, and CocoaPods
|
|
219
|
+
# refuses to install two vendored frameworks with the same name:
|
|
220
|
+
#
|
|
221
|
+
# [!] The 'Pods-YourApp' target has frameworks with conflicting names:
|
|
222
|
+
# opencv2.xcframework
|
|
223
|
+
#
|
|
224
|
+
# react-native-fast-opencv is the one this happens with, and wanting both is
|
|
225
|
+
# reasonable: our inference API with their image transformations. So when it
|
|
226
|
+
# is installed alongside us we depend on the pod it vendors instead of our
|
|
227
|
+
# own, which leaves exactly one opencv2 in the project. We only use
|
|
228
|
+
# `opencv2/core.hpp` and `opencv2/imgproc.hpp`, so any OpenCV 4.x build
|
|
229
|
+
# serves. Set "opencvPod" in the package.json config block to override the
|
|
230
|
+
# choice in either direction.
|
|
231
|
+
external_opencv = false
|
|
232
|
+
if enable_opencv
|
|
233
|
+
detected_opencv_pod =
|
|
234
|
+
if Dir.exist?(File.join(__dir__, "..", "react-native-fast-opencv"))
|
|
235
|
+
"FastOpenCV-iOS"
|
|
236
|
+
else
|
|
237
|
+
"opencv-rne"
|
|
238
|
+
end
|
|
239
|
+
opencv_pod = rne_build_config["opencvPod"] || detected_opencv_pod
|
|
240
|
+
|
|
241
|
+
if opencv_pod == "opencv-rne"
|
|
242
|
+
s.dependency "opencv-rne", "~> 4.11.0"
|
|
243
|
+
else
|
|
244
|
+
Pod::UI.puts "[react-native-executorch] using #{opencv_pod} for OpenCV " \
|
|
245
|
+
"instead of opencv-rne, so the project holds one opencv2" if defined?(Pod::UI)
|
|
246
|
+
s.dependency opencv_pod
|
|
247
|
+
external_opencv = true
|
|
248
|
+
end
|
|
249
|
+
end
|
|
250
|
+
|
|
251
|
+
# Our own OpenCV headers ship under third-party/include and are newer than
|
|
252
|
+
# what another OpenCV pod vendors: react-native-fast-opencv carries 4.9, and
|
|
253
|
+
# compiling against ours while linking against theirs fails at link time on
|
|
254
|
+
# any signature that moved since (cvtColor gained an AlgorithmHint parameter
|
|
255
|
+
# in 4.10). Whoever provides the binary has to provide the headers, so with
|
|
256
|
+
# an external OpenCV the include root becomes a mirror of ours with opencv2
|
|
257
|
+
# left out, and `#include <opencv2/...>` resolves through their framework.
|
|
258
|
+
mirror_without_opencv = lambda do
|
|
259
|
+
source = File.join(__dir__, "third-party/include")
|
|
260
|
+
mirror = File.join(__dir__, "third-party/include-external-opencv")
|
|
261
|
+
FileUtils.rm_rf(mirror)
|
|
262
|
+
FileUtils.mkdir_p(mirror)
|
|
263
|
+
Dir.children(source).each do |entry|
|
|
264
|
+
next if entry == "opencv2"
|
|
265
|
+
FileUtils.ln_s(File.join(source, entry), File.join(mirror, entry))
|
|
266
|
+
end
|
|
267
|
+
"third-party/include-external-opencv"
|
|
268
|
+
end
|
|
269
|
+
|
|
270
|
+
third_party_include =
|
|
271
|
+
external_opencv ? mirror_without_opencv.call : "third-party/include"
|
|
272
|
+
|
|
146
273
|
s.pod_target_xcconfig = {
|
|
147
274
|
"USE_HEADERMAP" => "YES",
|
|
148
275
|
"CLANG_CXX_LANGUAGE_STANDARD" => "c++20",
|
|
@@ -158,7 +285,7 @@ Pod::Spec.new do |s|
|
|
|
158
285
|
# ==============================================================================
|
|
159
286
|
"\"$(PODS_TARGET_SRCROOT)/legacy/cpp\"",
|
|
160
287
|
# ==============================================================================
|
|
161
|
-
"\"$(PODS_TARGET_SRCROOT)
|
|
288
|
+
"\"$(PODS_TARGET_SRCROOT)/#{third_party_include}\"",
|
|
162
289
|
"\"$(PODS_TARGET_SRCROOT)/third-party/include/cpuinfo\"",
|
|
163
290
|
"\"$(PODS_TARGET_SRCROOT)/third-party/include/pthreadpool\"",
|
|
164
291
|
"\"$(PODS_TARGET_SRCROOT)/third-party/include/executorch/extension/llm/tokenizers/include\"",
|
|
@@ -189,13 +316,23 @@ Pod::Spec.new do |s|
|
|
|
189
316
|
# resource path. `s.ios.resource` achieves that via CocoaPods' resource copy.
|
|
190
317
|
s.ios.resource = "third-party/ios/libs/executorch/mlx.metallib" if enable_mlx
|
|
191
318
|
|
|
319
|
+
# An app that turns on `use_frameworks!` without naming a linkage gets the
|
|
320
|
+
# default, dynamic - which is what Firebase's own setup instructions show.
|
|
321
|
+
# CocoaPods then refuses to install at all, because a dynamic framework may
|
|
322
|
+
# not carry statically linked binaries and opencv-rne vendors one:
|
|
323
|
+
#
|
|
324
|
+
# [!] The 'Pods-YourApp' target has transitive dependencies that include
|
|
325
|
+
# statically linked binaries: (.../opencv-rne/opencv2.xcframework)
|
|
326
|
+
#
|
|
327
|
+
# Declaring the pod a static framework resolves that without the app having
|
|
328
|
+
# to spell out `:linkage => :static`, and is inert when the pod is built as a
|
|
329
|
+
# static library, which is what happens with no `use_frameworks!` at all.
|
|
330
|
+
s.static_framework = true
|
|
331
|
+
|
|
192
332
|
# Backend xcframeworks are linked via force_load in OTHER_LDFLAGS (needed to
|
|
193
333
|
# preserve __attribute__((constructor)) backend registrations). Only
|
|
194
334
|
# ExecutorchLib goes in vendored_frameworks to avoid duplicate symbol errors.
|
|
195
335
|
s.ios.vendored_frameworks = ["third-party/ios/ExecutorchLib.xcframework"]
|
|
196
336
|
|
|
197
|
-
# iOS OpenCV is provided by the opencv-rne CocoaPod (not a downloaded tarball).
|
|
198
|
-
s.dependency "opencv-rne", "~> 4.11.0" if enable_opencv
|
|
199
|
-
|
|
200
337
|
install_modules_dependencies(s)
|
|
201
338
|
end
|
package/scripts/download-libs.js
CHANGED
|
@@ -172,32 +172,67 @@ const FEATURE_MAP = {
|
|
|
172
172
|
tokenizer: { backends: [], libs: [] },
|
|
173
173
|
};
|
|
174
174
|
|
|
175
|
-
|
|
176
|
-
|
|
175
|
+
/**
|
|
176
|
+
* The `react-native-executorch` block, and the package.json it came from.
|
|
177
|
+
*
|
|
178
|
+
* Two places are tried, in order:
|
|
179
|
+
*
|
|
180
|
+
* 1. INIT_CWD - where the install was invoked. For a single-app project that
|
|
181
|
+
* is the app itself.
|
|
182
|
+
* 2. Each package.json above this package. In a workspace, `yarn install` is
|
|
183
|
+
* run at the root, so INIT_CWD points there and a block in
|
|
184
|
+
* `apps/mobile/package.json` would never be seen. When the app keeps its
|
|
185
|
+
* own node_modules (pnpm, nohoist), walking up from here lands on the app.
|
|
186
|
+
*
|
|
187
|
+
* A hoisted workspace resolves to the root either way, which is where the block
|
|
188
|
+
* has to live in that layout - there is no way to tell which of several apps a
|
|
189
|
+
* root install was meant for.
|
|
190
|
+
* @returns The block and the path of the package.json holding it, or both
|
|
191
|
+
* `undefined` when no manifest declares one.
|
|
192
|
+
*/
|
|
193
|
+
function findUserConfig() {
|
|
194
|
+
const candidates = [];
|
|
195
|
+
const initCwd = process.env.INIT_CWD || process.env.npm_config_local_prefix;
|
|
196
|
+
if (initCwd) candidates.push(initCwd);
|
|
197
|
+
|
|
198
|
+
// `__dirname` is <somewhere>/node_modules/react-native-executorch/scripts.
|
|
199
|
+
let dir = path.resolve(__dirname, '..', '..', '..');
|
|
200
|
+
for (let i = 0; i < 6; i++) {
|
|
201
|
+
if (!candidates.includes(dir)) candidates.push(dir);
|
|
202
|
+
const parent = path.dirname(dir);
|
|
203
|
+
if (parent === dir) break;
|
|
204
|
+
dir = parent;
|
|
205
|
+
}
|
|
177
206
|
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
207
|
+
for (const root of candidates) {
|
|
208
|
+
const manifest = path.join(root, 'package.json');
|
|
209
|
+
let parsed;
|
|
210
|
+
try {
|
|
211
|
+
parsed = JSON.parse(fs.readFileSync(manifest, 'utf8'));
|
|
212
|
+
} catch {
|
|
213
|
+
continue;
|
|
214
|
+
}
|
|
215
|
+
if (parsed['react-native-executorch'] !== undefined) {
|
|
216
|
+
return { config: parsed['react-native-executorch'], manifest };
|
|
217
|
+
}
|
|
185
218
|
}
|
|
219
|
+
return { config: undefined, manifest: undefined };
|
|
220
|
+
}
|
|
186
221
|
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
'[react-native-executorch] Could not read app package.json, enabling all backends + libs.'
|
|
222
|
+
function readUserConfig() {
|
|
223
|
+
const allOn = () => ({ backends: [...ALL_BACKENDS], libs: [...ALL_LIBS], opencvPod: undefined });
|
|
224
|
+
|
|
225
|
+
const { config: rneConfig, manifest } = findUserConfig();
|
|
226
|
+
|
|
227
|
+
if (rneConfig === undefined) {
|
|
228
|
+
console.log(
|
|
229
|
+
'[react-native-executorch] No `react-native-executorch` block found; enabling all backends + libs.'
|
|
196
230
|
);
|
|
197
231
|
return allOn();
|
|
198
232
|
}
|
|
199
|
-
|
|
200
|
-
|
|
233
|
+
// Which manifest won matters when it is not the one the user edited - the
|
|
234
|
+
// usual monorepo surprise.
|
|
235
|
+
console.log(`[react-native-executorch] Read build config from ${manifest}`);
|
|
201
236
|
|
|
202
237
|
if (rneConfig.extras !== undefined) {
|
|
203
238
|
throw new Error(
|
|
@@ -236,10 +271,10 @@ function readUserConfig() {
|
|
|
236
271
|
}
|
|
237
272
|
}
|
|
238
273
|
|
|
239
|
-
return { backends: [...backends], libs: [...libs] };
|
|
274
|
+
return { backends: [...backends], libs: [...libs], opencvPod: rneConfig.opencvPod };
|
|
240
275
|
}
|
|
241
276
|
|
|
242
|
-
function writeBuildConfig({ backends, libs }) {
|
|
277
|
+
function writeBuildConfig({ backends, libs, opencvPod }) {
|
|
243
278
|
const config = {
|
|
244
279
|
enableOpencv: libs.includes('opencv'),
|
|
245
280
|
enablePhonemis: libs.includes('phonemis'),
|
|
@@ -248,6 +283,10 @@ function writeBuildConfig({ backends, libs }) {
|
|
|
248
283
|
enableMlx: backends.includes('mlx'),
|
|
249
284
|
enableVulkan: backends.includes('vulkan'),
|
|
250
285
|
};
|
|
286
|
+
// Which pod provides opencv2 on iOS. Only set when the app asks for a
|
|
287
|
+
// specific one; otherwise the podspec picks, preferring an OpenCV the app
|
|
288
|
+
// already carries so two frameworks named opencv2 never meet.
|
|
289
|
+
if (opencvPod !== undefined) config.opencvPod = opencvPod;
|
|
251
290
|
fs.writeFileSync(
|
|
252
291
|
path.join(PACKAGE_ROOT, 'rne-build-config.json'),
|
|
253
292
|
JSON.stringify(config, null, 2)
|
|
@@ -497,4 +536,4 @@ if (require.main === module) {
|
|
|
497
536
|
});
|
|
498
537
|
}
|
|
499
538
|
|
|
500
|
-
module.exports = { ALL_BACKENDS, ALL_LIBS, FEATURE_MAP };
|
|
539
|
+
module.exports = { ALL_BACKENDS, ALL_LIBS, FEATURE_MAP, findUserConfig, readUserConfig };
|
package/src/fetcher/telemetry.ts
CHANGED
|
@@ -10,7 +10,7 @@ const DOWNLOAD_EVENT_ENDPOINT = 'https://ai.swmansion.com/telemetry/downloads/ap
|
|
|
10
10
|
// self-referencing import would need package `exports` support in the consuming
|
|
11
11
|
// bundler to load at all. A wrong value here is analytics noise; a failed
|
|
12
12
|
// import would break the bundle.
|
|
13
|
-
const LIB_VERSION = '0.10.
|
|
13
|
+
const LIB_VERSION = '0.10.1';
|
|
14
14
|
|
|
15
15
|
// Anonymous analytics are on by default; apps opt out via setTelemetryEnabled.
|
|
16
16
|
let telemetryEnabled = true;
|