react-native-ultra-base64 0.1.5
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/LICENSE +20 -0
- package/README.md +378 -0
- package/android/CMakeLists.txt +34 -0
- package/android/build.gradle +107 -0
- package/android/cpp-adapter.cpp +12 -0
- package/android/gradle.properties +5 -0
- package/android/src/main/AndroidManifest.xml +2 -0
- package/android/src/main/java/com/ultrabase64/UltraBase64Module.kt +38 -0
- package/android/src/main/java/com/ultrabase64/UltraBase64Package.kt +16 -0
- package/cpp/react-native-ultra-base64.cpp +147 -0
- package/cpp/react-native-ultra-base64.h +13 -0
- package/cpp/simdutf.cpp +68045 -0
- package/cpp/simdutf.h +13941 -0
- package/ios/UltraBase64.h +6 -0
- package/ios/UltraBase64.mm +41 -0
- package/lib/commonjs/index.js +78 -0
- package/lib/commonjs/index.js.map +1 -0
- package/lib/commonjs/package.json +1 -0
- package/lib/module/index.js +68 -0
- package/lib/module/index.js.map +1 -0
- package/lib/module/package.json +1 -0
- package/lib/typescript/index.d.ts +22 -0
- package/lib/typescript/index.d.ts.map +1 -0
- package/package.json +128 -0
- package/react-native-ultra-base64.podspec +39 -0
- package/src/index.tsx +93 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Alex Shumihin
|
|
4
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
5
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
6
|
+
in the Software without restriction, including without limitation the rights
|
|
7
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
8
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
9
|
+
furnished to do so, subject to the following conditions:
|
|
10
|
+
|
|
11
|
+
The above copyright notice and this permission notice shall be included in all
|
|
12
|
+
copies or substantial portions of the Software.
|
|
13
|
+
|
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
15
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
16
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
17
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
18
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
19
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
20
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,378 @@
|
|
|
1
|
+
# ⚡ react-native-ultra-base64
|
|
2
|
+
|
|
3
|
+
**The fastest base64 encoding/decoding library for React Native**
|
|
4
|
+
|
|
5
|
+
Ultra-fast base64 operations powered by optimized C++ with JSI bindings. Built for performance-critical applications that need blazing-fast base64 encoding and decoding.
|
|
6
|
+
|
|
7
|
+
[](https://www.npmjs.com/package/react-native-ultra-base64)
|
|
8
|
+
[](https://github.com/pioner92/react-native-ultra-base64/blob/main/LICENSE)
|
|
9
|
+
[](https://github.com/pioner92/react-native-ultra-base64)
|
|
10
|
+
|
|
11
|
+
---
|
|
12
|
+
|
|
13
|
+
## 🚀 Why Choose This Library?
|
|
14
|
+
|
|
15
|
+
- **🏎️ Blazing Fast** - Up to **2x faster** than react-native-quick-base64 v3
|
|
16
|
+
- **⚡ Zero Bridge Overhead** - Direct JSI bindings eliminate React Native bridge bottleneck
|
|
17
|
+
- **🌐 URL-Safe Support** - Native support for URL-safe base64 encoding/decoding
|
|
18
|
+
- **📦 Small Bundle** - Minimal JavaScript footprint, heavy lifting done in native code
|
|
19
|
+
- **🔒 Type Safe** - Full TypeScript support with comprehensive type definitions
|
|
20
|
+
- **✅ Battle Tested** - Extensive test suite covering edge cases and compatibility
|
|
21
|
+
|
|
22
|
+
---
|
|
23
|
+
|
|
24
|
+
## 📊 Performance
|
|
25
|
+
|
|
26
|
+
Benchmark against **react-native-quick-base64 v3**
|
|
27
|
+
|
|
28
|
+
| iPhone | Android |
|
|
29
|
+
| ------ | ------- |
|
|
30
|
+
| <img src="./assets/iphone.png" height="600"> | <img src="./assets/android.png" height="600"> |
|
|
31
|
+
|
|
32
|
+
|
|
33
|
+
> 💡 **Performance scales with data size** - the larger your data, the more dramatic the improvement!
|
|
34
|
+
|
|
35
|
+
---
|
|
36
|
+
|
|
37
|
+
## 📦 Installation
|
|
38
|
+
|
|
39
|
+
```sh
|
|
40
|
+
npm install react-native-ultra-base64
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
or
|
|
44
|
+
|
|
45
|
+
```sh
|
|
46
|
+
yarn add react-native-ultra-base64
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
### iOS Setup
|
|
50
|
+
|
|
51
|
+
```sh
|
|
52
|
+
cd ios && pod install
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
### Android Setup
|
|
56
|
+
|
|
57
|
+
No additional steps required! The library will automatically link.
|
|
58
|
+
|
|
59
|
+
---
|
|
60
|
+
|
|
61
|
+
## 🎯 Quick Start
|
|
62
|
+
|
|
63
|
+
```typescript
|
|
64
|
+
import {
|
|
65
|
+
fromByteArray,
|
|
66
|
+
toByteArray,
|
|
67
|
+
byteLength,
|
|
68
|
+
trimBase64Padding
|
|
69
|
+
} from 'react-native-ultra-base64';
|
|
70
|
+
|
|
71
|
+
// 🔵 Encode to base64
|
|
72
|
+
const data = new Uint8Array([72, 101, 108, 108, 111]);
|
|
73
|
+
const encoded = fromByteArray(data);
|
|
74
|
+
console.log(encoded); // "SGVsbG8="
|
|
75
|
+
|
|
76
|
+
// 🔵 Decode from base64
|
|
77
|
+
const decoded = toByteArray('SGVsbG8=');
|
|
78
|
+
console.log(decoded); // Uint8Array [72, 101, 108, 108, 111]
|
|
79
|
+
|
|
80
|
+
// 🔵 Get byte length without decoding
|
|
81
|
+
const length = byteLength('SGVsbG8=');
|
|
82
|
+
console.log(length); // 5
|
|
83
|
+
|
|
84
|
+
// 🔵 URL-safe base64
|
|
85
|
+
const urlSafeEncoded = fromByteArray(data, true);
|
|
86
|
+
console.log(urlSafeEncoded); // Uses '-' and '_' instead of '+' and '/'
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
---
|
|
90
|
+
|
|
91
|
+
## 📖 API Reference
|
|
92
|
+
|
|
93
|
+
### `fromByteArray(uint8: Uint8Array, urlSafe?: boolean): string`
|
|
94
|
+
|
|
95
|
+
Encodes a `Uint8Array` to a base64 string.
|
|
96
|
+
|
|
97
|
+
**Parameters:**
|
|
98
|
+
- `uint8` - The byte array to encode
|
|
99
|
+
- `urlSafe` (optional) - Use URL-safe encoding (replaces `+/` with `-_` and omits padding)
|
|
100
|
+
|
|
101
|
+
**Returns:** Base64 encoded string
|
|
102
|
+
|
|
103
|
+
**Example:**
|
|
104
|
+
```typescript
|
|
105
|
+
const bytes = new Uint8Array([255, 254, 253]);
|
|
106
|
+
const standard = fromByteArray(bytes); // "//79"
|
|
107
|
+
const urlSafe = fromByteArray(bytes, true); // "__79"
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
---
|
|
111
|
+
|
|
112
|
+
### `toByteArray(input: string, removeLinebreaks?: boolean): Uint8Array`
|
|
113
|
+
|
|
114
|
+
Decodes a base64 string to a `Uint8Array`.
|
|
115
|
+
|
|
116
|
+
**Parameters:**
|
|
117
|
+
- `input` - The base64 string to decode
|
|
118
|
+
- `removeLinebreaks` (optional) - Remove `\n` and `\r` before decoding
|
|
119
|
+
|
|
120
|
+
**Returns:** Decoded byte array
|
|
121
|
+
|
|
122
|
+
**Example:**
|
|
123
|
+
```typescript
|
|
124
|
+
const decoded = toByteArray('SGVsbG8=');
|
|
125
|
+
console.log(decoded); // Uint8Array [72, 101, 108, 108, 111]
|
|
126
|
+
|
|
127
|
+
// Handle base64 with linebreaks
|
|
128
|
+
const withLinebreaks = 'SGVs\nbG8=';
|
|
129
|
+
const cleaned = toByteArray(withLinebreaks, true);
|
|
130
|
+
```
|
|
131
|
+
|
|
132
|
+
**Throws:** `Error` if input is not valid base64
|
|
133
|
+
|
|
134
|
+
---
|
|
135
|
+
|
|
136
|
+
### `byteLength(b64: string): number`
|
|
137
|
+
|
|
138
|
+
Calculates the byte length of a base64 string **without decoding**.
|
|
139
|
+
|
|
140
|
+
**Parameters:**
|
|
141
|
+
- `b64` - The base64 string
|
|
142
|
+
|
|
143
|
+
**Returns:** Number of bytes the decoded data would be
|
|
144
|
+
|
|
145
|
+
**Example:**
|
|
146
|
+
```typescript
|
|
147
|
+
const length = byteLength('SGVsbG8=');
|
|
148
|
+
console.log(length); // 5 (much faster than decoding)
|
|
149
|
+
```
|
|
150
|
+
|
|
151
|
+
---
|
|
152
|
+
|
|
153
|
+
### `trimBase64Padding(str: string): string`
|
|
154
|
+
|
|
155
|
+
Removes trailing padding characters (`=`) from a base64 string.
|
|
156
|
+
|
|
157
|
+
**Parameters:**
|
|
158
|
+
- `str` - The base64 string
|
|
159
|
+
|
|
160
|
+
**Returns:** String without padding
|
|
161
|
+
|
|
162
|
+
**Example:**
|
|
163
|
+
```typescript
|
|
164
|
+
const padded = 'SGVsbG8=';
|
|
165
|
+
const trimmed = trimBase64Padding(padded);
|
|
166
|
+
console.log(trimmed); // "SGVsbG8"
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
## 🎨 Advanced Examples
|
|
170
|
+
|
|
171
|
+
### Working with Images
|
|
172
|
+
|
|
173
|
+
```typescript
|
|
174
|
+
import { toByteArray, fromByteArray } from 'react-native-ultra-base64';
|
|
175
|
+
import RNFS from 'react-native-fs';
|
|
176
|
+
|
|
177
|
+
// Load and decode base64 image
|
|
178
|
+
async function loadImage(base64Data: string) {
|
|
179
|
+
const imageBytes = toByteArray(base64Data);
|
|
180
|
+
const path = `${RNFS.CachesDirectoryPath}/image.jpg`;
|
|
181
|
+
await RNFS.writeFile(path, imageBytes, 'base64');
|
|
182
|
+
return path;
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
// Encode image to base64
|
|
186
|
+
async function encodeImage(filePath: string) {
|
|
187
|
+
const fileData = await RNFS.readFile(filePath, 'base64');
|
|
188
|
+
const bytes = toByteArray(fileData);
|
|
189
|
+
return fromByteArray(bytes);
|
|
190
|
+
}
|
|
191
|
+
```
|
|
192
|
+
|
|
193
|
+
### Processing Large Files
|
|
194
|
+
|
|
195
|
+
```typescript
|
|
196
|
+
import { toByteArray, fromByteArray } from 'react-native-ultra-base64';
|
|
197
|
+
|
|
198
|
+
// Efficiently process large base64 data
|
|
199
|
+
function processLargeFile(base64String: string) {
|
|
200
|
+
// Decode (fast!)
|
|
201
|
+
const bytes = toByteArray(base64String);
|
|
202
|
+
|
|
203
|
+
// Process bytes...
|
|
204
|
+
const processed = bytes.map(byte => byte ^ 0xFF); // Example: invert bits
|
|
205
|
+
|
|
206
|
+
// Encode back (still fast!)
|
|
207
|
+
return fromByteArray(new Uint8Array(processed));
|
|
208
|
+
}
|
|
209
|
+
```
|
|
210
|
+
|
|
211
|
+
### API Requests with Base64 Bodies
|
|
212
|
+
|
|
213
|
+
```typescript
|
|
214
|
+
import { fromByteArray, toByteArray } from 'react-native-ultra-base64';
|
|
215
|
+
|
|
216
|
+
// Send binary data as base64
|
|
217
|
+
async function uploadBinaryData(data: Uint8Array) {
|
|
218
|
+
const base64 = fromByteArray(data);
|
|
219
|
+
|
|
220
|
+
const response = await fetch('https://api.example.com/upload', {
|
|
221
|
+
method: 'POST',
|
|
222
|
+
headers: { 'Content-Type': 'application/json' },
|
|
223
|
+
body: JSON.stringify({ data: base64 })
|
|
224
|
+
});
|
|
225
|
+
|
|
226
|
+
return response.json();
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
// Receive binary data as base64
|
|
230
|
+
async function downloadBinaryData() {
|
|
231
|
+
const response = await fetch('https://api.example.com/download');
|
|
232
|
+
const { data } = await response.json();
|
|
233
|
+
|
|
234
|
+
return toByteArray(data); // Returns Uint8Array
|
|
235
|
+
}
|
|
236
|
+
```
|
|
237
|
+
|
|
238
|
+
### Crypto Integration
|
|
239
|
+
|
|
240
|
+
```typescript
|
|
241
|
+
import { toByteArray, fromByteArray } from 'react-native-ultra-base64';
|
|
242
|
+
import * as Crypto from 'expo-crypto';
|
|
243
|
+
|
|
244
|
+
async function encryptAndEncode(plaintext: string) {
|
|
245
|
+
// Encrypt
|
|
246
|
+
const encrypted = await Crypto.digestStringAsync(
|
|
247
|
+
Crypto.CryptoDigestAlgorithm.SHA256,
|
|
248
|
+
plaintext,
|
|
249
|
+
{ encoding: Crypto.CryptoEncoding.HEX }
|
|
250
|
+
);
|
|
251
|
+
|
|
252
|
+
// Convert hex to bytes
|
|
253
|
+
const bytes = new Uint8Array(
|
|
254
|
+
encrypted.match(/.{1,2}/g)!.map(byte => parseInt(byte, 16))
|
|
255
|
+
);
|
|
256
|
+
|
|
257
|
+
// Encode to base64 for transmission
|
|
258
|
+
return fromByteArray(bytes);
|
|
259
|
+
}
|
|
260
|
+
```
|
|
261
|
+
|
|
262
|
+
---
|
|
263
|
+
|
|
264
|
+
## 🔥 Features
|
|
265
|
+
|
|
266
|
+
- ✅ **Standard & URL-safe base64** - Full RFC 4648 compliance
|
|
267
|
+
- ✅ **Linebreak handling** - Automatically remove `\n` and `\r` during decode
|
|
268
|
+
- ✅ **Padding tolerance** - Handles missing or misplaced padding gracefully
|
|
269
|
+
- ✅ **TypeScript first** - Complete type definitions included
|
|
270
|
+
- ✅ **Zero dependencies** - No runtime dependencies except React Native
|
|
271
|
+
- ✅ **JSI direct bindings** - Bypass the bridge entirely
|
|
272
|
+
- ✅ **Memory efficient** - Optimized memory usage for large data
|
|
273
|
+
- ✅ **Works with Expo** - Compatible with Expo dev builds
|
|
274
|
+
|
|
275
|
+
---
|
|
276
|
+
|
|
277
|
+
## 🆚 Comparison with react-native-quick-base64
|
|
278
|
+
|
|
279
|
+
| Feature | react-native-ultra-base64 | react-native-quick-base64 |
|
|
280
|
+
|---------|--------------------------|---------------------------|
|
|
281
|
+
| **Speed** | ⚡⚡⚡⚡⚡ ~2x faster | ⚡⚡⚡ Fast |
|
|
282
|
+
| **JSI Bindings** | ✅ | ✅ |
|
|
283
|
+
| **URL-safe Support** | ✅ | ✅ |
|
|
284
|
+
| **TypeScript** | ✅ | ✅ |
|
|
285
|
+
| **Bundle Size** | 🟢 Small | 🟢 Small |
|
|
286
|
+
| **Native Code** | C++ (highly optimized) | C++ |
|
|
287
|
+
|
|
288
|
+
---
|
|
289
|
+
|
|
290
|
+
## 🏗️ How It Works
|
|
291
|
+
|
|
292
|
+
This library uses several optimization techniques:
|
|
293
|
+
|
|
294
|
+
1. **JSI Direct Bindings** - Functions are installed directly on the JavaScript global object, eliminating bridge serialization overhead
|
|
295
|
+
2. **Cache-Aligned Tables** - Lookup tables are aligned to 64-byte boundaries for L1 cache efficiency
|
|
296
|
+
3. **Branch Prediction Hints** - Uses `[[likely]]`/`[[unlikely]]` attributes for optimal branch prediction
|
|
297
|
+
4. **Zero-Copy Operations** - Direct memory access to ArrayBuffers without copying when possible
|
|
298
|
+
5. **Optimized Hot Paths** - Fast path for common cases (99.9%), slow path only for edge cases
|
|
299
|
+
|
|
300
|
+
---
|
|
301
|
+
|
|
302
|
+
## 🐛 Troubleshooting
|
|
303
|
+
|
|
304
|
+
### "encodeBase64FromArrayBuffer is not a function"
|
|
305
|
+
|
|
306
|
+
Make sure the native module is properly installed and linked:
|
|
307
|
+
|
|
308
|
+
```sh
|
|
309
|
+
# iOS
|
|
310
|
+
cd ios && pod install
|
|
311
|
+
|
|
312
|
+
# Clean build
|
|
313
|
+
cd .. && yarn example ios --simulator="iPhone 15"
|
|
314
|
+
```
|
|
315
|
+
|
|
316
|
+
### TypeScript errors
|
|
317
|
+
|
|
318
|
+
Ensure you have the latest version installed and TypeScript can find the types:
|
|
319
|
+
|
|
320
|
+
```json
|
|
321
|
+
// tsconfig.json
|
|
322
|
+
{
|
|
323
|
+
"compilerOptions": {
|
|
324
|
+
"moduleResolution": "node"
|
|
325
|
+
}
|
|
326
|
+
}
|
|
327
|
+
```
|
|
328
|
+
|
|
329
|
+
### Performance not as expected?
|
|
330
|
+
|
|
331
|
+
- Ensure you're running a **release build** (debug builds have overhead)
|
|
332
|
+
- Check you're testing with realistic data sizes (>1KB)
|
|
333
|
+
- Verify no other libraries are intercepting base64 operations
|
|
334
|
+
|
|
335
|
+
---
|
|
336
|
+
|
|
337
|
+
## 🤝 Contributing
|
|
338
|
+
|
|
339
|
+
Contributions are welcome! Please see [CONTRIBUTING.md](CONTRIBUTING.md) for details.
|
|
340
|
+
|
|
341
|
+
### Development Setup
|
|
342
|
+
|
|
343
|
+
```sh
|
|
344
|
+
# Clone the repo
|
|
345
|
+
git clone https://github.com/pioner92/react-native-ultra-base64.git
|
|
346
|
+
cd react-native-ultra-base64
|
|
347
|
+
|
|
348
|
+
# Install dependencies
|
|
349
|
+
yarn
|
|
350
|
+
|
|
351
|
+
# Run example app
|
|
352
|
+
yarn example ios
|
|
353
|
+
# or
|
|
354
|
+
yarn example android
|
|
355
|
+
```
|
|
356
|
+
|
|
357
|
+
---
|
|
358
|
+
|
|
359
|
+
## 📄 License
|
|
360
|
+
|
|
361
|
+
MIT © [Alex Shumihin](https://github.com/pioner92)
|
|
362
|
+
|
|
363
|
+
---
|
|
364
|
+
|
|
365
|
+
## 🙏 Acknowledgments
|
|
366
|
+
|
|
367
|
+
- Inspired by [base64-js](https://github.com/beatgammit/base64-js) and [react-native-quick-base64](https://github.com/craftzdog/react-native-quick-base64)
|
|
368
|
+
- Built with [create-react-native-library](https://github.com/callstack/react-native-builder-bob)
|
|
369
|
+
|
|
370
|
+
---
|
|
371
|
+
|
|
372
|
+
## ⭐ Show Your Support
|
|
373
|
+
|
|
374
|
+
If this library helps your project, please give it a ⭐ on [GitHub](https://github.com/pioner92/react-native-ultra-base64)!
|
|
375
|
+
|
|
376
|
+
---
|
|
377
|
+
|
|
378
|
+
**Made with ❤️ for the React Native community**
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
cmake_minimum_required(VERSION 3.4.1)
|
|
2
|
+
project(react-native-ultra-base64)
|
|
3
|
+
|
|
4
|
+
set (CMAKE_VERBOSE_MAKEFILE ON)
|
|
5
|
+
set (CMAKE_CXX_STANDARD 17)
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
add_library(react-native-ultra-base64 SHARED
|
|
9
|
+
../cpp/react-native-ultra-base64.cpp
|
|
10
|
+
../cpp/simdutf.cpp
|
|
11
|
+
../cpp/simdutf.h
|
|
12
|
+
cpp-adapter.cpp
|
|
13
|
+
)
|
|
14
|
+
|
|
15
|
+
include_directories(
|
|
16
|
+
../cpp
|
|
17
|
+
)
|
|
18
|
+
|
|
19
|
+
find_package(ReactAndroid REQUIRED CONFIG)
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
if (ReactAndroid_VERSION_MINOR GREATER_EQUAL 76)
|
|
23
|
+
target_link_libraries(
|
|
24
|
+
react-native-ultra-base64
|
|
25
|
+
ReactAndroid::jsi
|
|
26
|
+
ReactAndroid::reactnative
|
|
27
|
+
)
|
|
28
|
+
else()
|
|
29
|
+
target_link_libraries(
|
|
30
|
+
react-native-ultra-base64
|
|
31
|
+
ReactAndroid::jsi
|
|
32
|
+
ReactAndroid::reactnativejni
|
|
33
|
+
)
|
|
34
|
+
endif()
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
buildscript {
|
|
2
|
+
def kotlin_version = rootProject.ext.has("kotlinVersion") ? rootProject.ext.get("kotlinVersion") : project.properties["RNUltraBase64_kotlinVersion"]
|
|
3
|
+
|
|
4
|
+
repositories {
|
|
5
|
+
google()
|
|
6
|
+
mavenCentral()
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
dependencies {
|
|
10
|
+
classpath "com.android.tools.build:gradle:7.2.1"
|
|
11
|
+
// noinspection DifferentKotlinGradleVersion
|
|
12
|
+
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
|
|
13
|
+
}
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
def reactNativeArchitectures() {
|
|
18
|
+
def value = rootProject.getProperties().get("reactNativeArchitectures")
|
|
19
|
+
return value ? value.split(",") : ["armeabi-v7a", "x86", "x86_64", "arm64-v8a"]
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
def isNewArchitectureEnabled() {
|
|
23
|
+
return rootProject.hasProperty("newArchEnabled") && rootProject.getProperty("newArchEnabled") == "true"
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
def getExtOrDefault(name) {
|
|
27
|
+
return rootProject.ext.has(name) ? rootProject.ext.get(name) : project.properties["RNUlid_" + name]
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
def getExtOrIntegerDefault(name) {
|
|
31
|
+
return rootProject.ext.has(name) ? rootProject.ext.get(name) : (project.properties["RNUlid_" + name]).toInteger()
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
apply plugin: "com.android.library"
|
|
36
|
+
apply plugin: "kotlin-android"
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
if (isNewArchitectureEnabled()) {
|
|
40
|
+
apply plugin: "com.facebook.react"
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
android {
|
|
44
|
+
namespace "com.ultrabase64"
|
|
45
|
+
|
|
46
|
+
compileSdkVersion getExtOrDefault("compileSdkVersion")
|
|
47
|
+
|
|
48
|
+
defaultConfig {
|
|
49
|
+
minSdkVersion getExtOrDefault("minSdkVersion")
|
|
50
|
+
targetSdkVersion getExtOrDefault("targetSdkVersion")
|
|
51
|
+
|
|
52
|
+
externalNativeBuild {
|
|
53
|
+
cmake {
|
|
54
|
+
cppFlags "-O3 -Wall -ffunction-sections -fdata-sections -fstack-protector-strong"
|
|
55
|
+
abiFilters (*reactNativeArchitectures())
|
|
56
|
+
arguments "-DANDROID_STL=c++_shared",
|
|
57
|
+
"-DANDROID_SUPPORT_FLEXIBLE_PAGE_SIZES=ON"
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
externalNativeBuild {
|
|
63
|
+
cmake {
|
|
64
|
+
path "CMakeLists.txt"
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
buildFeatures {
|
|
69
|
+
buildConfig true
|
|
70
|
+
prefab true
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
buildTypes {
|
|
74
|
+
release {
|
|
75
|
+
minifyEnabled false
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
packagingOptions {
|
|
80
|
+
excludes = [
|
|
81
|
+
"**/libc++_shared.so",
|
|
82
|
+
"**/libjsi.so",
|
|
83
|
+
"**/libreactnativejni.so",
|
|
84
|
+
"**/libreact_nativemodule_core.so",
|
|
85
|
+
"**/libturbomodulejsijni.so",
|
|
86
|
+
"**/libc++_shared.so",
|
|
87
|
+
"**/libfbjni.so",
|
|
88
|
+
"**/libreactnative.so",
|
|
89
|
+
]
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
lint {
|
|
93
|
+
disable "GradleCompatible"
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
compileOptions {
|
|
97
|
+
sourceCompatibility JavaVersion.VERSION_1_8
|
|
98
|
+
targetCompatibility JavaVersion.VERSION_1_8
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
def kotlin_version = getExtOrDefault("kotlinVersion")
|
|
103
|
+
|
|
104
|
+
dependencies {
|
|
105
|
+
implementation "com.facebook.react:react-native:+"
|
|
106
|
+
implementation "org.jetbrains.kotlin:kotlin-stdlib:$kotlin_version"
|
|
107
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
#include <jni.h>
|
|
2
|
+
#include "jsi/jsi.h"
|
|
3
|
+
#include "react-native-ultra-base64.h"
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
extern "C"
|
|
7
|
+
JNIEXPORT void JNICALL
|
|
8
|
+
Java_com_ultrabase64_UltraBase64Module_nativeInstall (JNIEnv* /*env*/, jobject /*thiz*/, jlong runtimePtr) {
|
|
9
|
+
auto* rt = reinterpret_cast<facebook::jsi::Runtime*>(runtimePtr);
|
|
10
|
+
if (!rt) return;
|
|
11
|
+
rnub_base64::install(rt);
|
|
12
|
+
}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
package com.ultrabase64
|
|
2
|
+
|
|
3
|
+
import android.util.Log
|
|
4
|
+
import com.facebook.react.bridge.ReactApplicationContext
|
|
5
|
+
import com.facebook.react.bridge.ReactContextBaseJavaModule
|
|
6
|
+
import com.facebook.react.bridge.ReactMethod
|
|
7
|
+
import com.facebook.react.common.annotations.FrameworkAPI
|
|
8
|
+
|
|
9
|
+
class UltraBase64Module(private val reactContext: ReactApplicationContext) :
|
|
10
|
+
ReactContextBaseJavaModule(reactContext) {
|
|
11
|
+
|
|
12
|
+
override fun getName(): String {
|
|
13
|
+
return NAME
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
companion object {
|
|
17
|
+
const val NAME = "RNUltraBase64"
|
|
18
|
+
init {
|
|
19
|
+
System.loadLibrary("react-native-ultra-base64")
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
@OptIn(FrameworkAPI::class)
|
|
23
|
+
@JvmStatic
|
|
24
|
+
private external fun nativeInstall(jsiRuntimePtr: Long)
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
@OptIn(FrameworkAPI::class)
|
|
28
|
+
@ReactMethod(isBlockingSynchronousMethod = true)
|
|
29
|
+
fun install(): Boolean {
|
|
30
|
+
Log.d("react-native-ultra-base64", "install() called")
|
|
31
|
+
nativeInstall(
|
|
32
|
+
reactContext.javaScriptContextHolder!!.get(),
|
|
33
|
+
)
|
|
34
|
+
return true
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
package com.ultrabase64
|
|
2
|
+
|
|
3
|
+
import com.facebook.react.ReactPackage
|
|
4
|
+
import com.facebook.react.bridge.NativeModule
|
|
5
|
+
import com.facebook.react.bridge.ReactApplicationContext
|
|
6
|
+
import com.facebook.react.uimanager.ViewManager
|
|
7
|
+
|
|
8
|
+
class UltraBase64Package : ReactPackage {
|
|
9
|
+
override fun createNativeModules(reactContext: ReactApplicationContext): List<NativeModule> {
|
|
10
|
+
return listOf(UltraBase64Module(reactContext))
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
override fun createViewManagers(reactContext: ReactApplicationContext): List<ViewManager<*, *>> {
|
|
14
|
+
return emptyList()
|
|
15
|
+
}
|
|
16
|
+
}
|