mirror of
https://gitcode.com/gh_mirrors/re/react-native-pushy.git
synced 2025-09-16 13:01:38 +08:00
Compare commits
21 Commits
Author | SHA1 | Date | |
---|---|---|---|
![]() |
d666e8c0f3 | ||
![]() |
5e89fb4a25 | ||
![]() |
ab01b6010a | ||
![]() |
92bc830d98 | ||
![]() |
7531e8ca3a | ||
![]() |
b2305cff3f | ||
![]() |
c5cdb6031b | ||
![]() |
20ebf8979e | ||
![]() |
3929fc2f8e | ||
![]() |
31ee269717 | ||
![]() |
adcd57b6b5 | ||
![]() |
c595e4e54a | ||
![]() |
4f80f96a8d | ||
![]() |
a77c3c85f3 | ||
![]() |
2357a0b78d | ||
![]() |
88bacdfb15 | ||
![]() |
90fee03c45 | ||
![]() |
7243512d3c | ||
![]() |
11b383d10b | ||
![]() |
af65b2660c | ||
![]() |
28b8e122af |
@@ -94,7 +94,7 @@ apply from: "../../node_modules/react-native/react.gradle"
|
||||
* Upload all the APKs to the Play Store and people will download
|
||||
* the correct one based on the CPU architecture of their device.
|
||||
*/
|
||||
def enableSeparateBuildPerCPUArchitecture = false
|
||||
def enableSeparateBuildPerCPUArchitecture = true
|
||||
|
||||
/**
|
||||
* Run Proguard to shrink the Java bytecode in release builds.
|
||||
@@ -141,7 +141,7 @@ android {
|
||||
minSdkVersion rootProject.ext.minSdkVersion
|
||||
targetSdkVersion rootProject.ext.targetSdkVersion
|
||||
versionCode 1
|
||||
versionName "1.0"
|
||||
versionName "2.0"
|
||||
testBuildType System.getProperty('testBuildType', 'debug')
|
||||
testInstrumentationRunner 'androidx.test.runner.AndroidJUnitRunner'
|
||||
buildConfigField "boolean", "IS_NEW_ARCHITECTURE_ENABLED", isNewArchitectureEnabled().toString()
|
||||
@@ -237,6 +237,7 @@ android {
|
||||
release {
|
||||
// Caution! In production, you need to generate your own keystore file.
|
||||
// see https://reactnative.dev/docs/signed-apk-android.
|
||||
crunchPngs false
|
||||
signingConfig signingConfigs.debug
|
||||
minifyEnabled enableProguardInReleaseBuilds
|
||||
proguardFiles getDefaultProguardFile("proguard-android.txt"), "proguard-rules.pro"
|
||||
|
@@ -2,6 +2,8 @@
|
||||
package="com.awesomeproject">
|
||||
|
||||
<uses-permission android:name="android.permission.INTERNET" />
|
||||
<uses-permission android:name="android.permission.CAMERA" />
|
||||
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
|
||||
|
||||
<application
|
||||
android:name=".MainApplication"
|
||||
@@ -19,8 +21,14 @@
|
||||
android:windowSoftInputMode="adjustResize"
|
||||
android:exported="true">
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.MAIN" />
|
||||
<category android:name="android.intent.category.LAUNCHER" />
|
||||
<action android:name="android.intent.action.MAIN" />
|
||||
<category android:name="android.intent.category.LAUNCHER" />
|
||||
</intent-filter>
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.VIEW" />
|
||||
<category android:name="android.intent.category.DEFAULT" />
|
||||
<category android:name="android.intent.category.BROWSABLE" />
|
||||
<data android:scheme="testhotupdate" />
|
||||
</intent-filter>
|
||||
</activity>
|
||||
</application>
|
||||
|
@@ -5,10 +5,11 @@ import org.apache.tools.ant.taskdefs.condition.Os
|
||||
buildscript {
|
||||
ext {
|
||||
buildToolsVersion = "31.0.0"
|
||||
minSdkVersion = 21
|
||||
minSdkVersion = 23
|
||||
compileSdkVersion = 31
|
||||
targetSdkVersion = 31
|
||||
kotlinVersion = '1.6.10'
|
||||
kotlinVersion = '1.7.20'
|
||||
kotlin_version = '1.7.20'
|
||||
|
||||
if (System.properties['os.arch'] == "aarch64") {
|
||||
// For M1 Users we need to use the NDK 24 which added support for aarch64
|
||||
|
@@ -53,5 +53,10 @@
|
||||
</array>
|
||||
<key>UIViewControllerBasedStatusBarAppearance</key>
|
||||
<false/>
|
||||
<key>NSCameraUsageDescription</key>
|
||||
<string>For taking photos</string>
|
||||
|
||||
<key>NSPhotoLibraryUsageDescription</key>
|
||||
<string>For saving photos</string>
|
||||
</dict>
|
||||
</plist>
|
||||
|
@@ -222,17 +222,17 @@ PODS:
|
||||
- glog
|
||||
- react-native-safe-area-context (4.8.2):
|
||||
- React-Core
|
||||
- react-native-update (10.7.1):
|
||||
- react-native-update (10.10.0):
|
||||
- React
|
||||
- React-Core
|
||||
- react-native-update/HDiffPatch (= 10.7.1)
|
||||
- react-native-update/RCTPushy (= 10.7.1)
|
||||
- react-native-update/HDiffPatch (= 10.10.0)
|
||||
- react-native-update/RCTPushy (= 10.10.0)
|
||||
- SSZipArchive
|
||||
- react-native-update/HDiffPatch (10.7.1):
|
||||
- react-native-update/HDiffPatch (10.10.0):
|
||||
- React
|
||||
- React-Core
|
||||
- SSZipArchive
|
||||
- react-native-update/RCTPushy (10.7.1):
|
||||
- react-native-update/RCTPushy (10.10.0):
|
||||
- React
|
||||
- React-Core
|
||||
- SSZipArchive
|
||||
@@ -302,6 +302,8 @@ PODS:
|
||||
- React-jsi (= 0.69.8)
|
||||
- React-logger (= 0.69.8)
|
||||
- React-perflogger (= 0.69.8)
|
||||
- ReactNativeCameraKit (14.0.0-beta9):
|
||||
- React-Core
|
||||
- RNVectorIcons (10.0.3):
|
||||
- React-Core
|
||||
- SSZipArchive (2.4.3)
|
||||
@@ -342,6 +344,7 @@ DEPENDENCIES:
|
||||
- React-RCTVibration (from `../node_modules/react-native/Libraries/Vibration`)
|
||||
- React-runtimeexecutor (from `../node_modules/react-native/ReactCommon/runtimeexecutor`)
|
||||
- ReactCommon/turbomodule/core (from `../node_modules/react-native/ReactCommon`)
|
||||
- ReactNativeCameraKit (from `../node_modules/react-native-camera-kit`)
|
||||
- RNVectorIcons (from `../node_modules/react-native-vector-icons`)
|
||||
- Yoga (from `../node_modules/react-native/ReactCommon/yoga`)
|
||||
|
||||
@@ -417,6 +420,8 @@ EXTERNAL SOURCES:
|
||||
:path: "../node_modules/react-native/ReactCommon/runtimeexecutor"
|
||||
ReactCommon:
|
||||
:path: "../node_modules/react-native/ReactCommon"
|
||||
ReactNativeCameraKit:
|
||||
:path: "../node_modules/react-native-camera-kit"
|
||||
RNVectorIcons:
|
||||
:path: "../node_modules/react-native-vector-icons"
|
||||
Yoga:
|
||||
@@ -444,7 +449,7 @@ SPEC CHECKSUMS:
|
||||
React-jsinspector: 0eda09e9cf22bbb5dbb1d23143b03a31acf37d67
|
||||
React-logger: 5997ab008583826c10ffe4e1ff990363e975639d
|
||||
react-native-safe-area-context: 0ee144a6170530ccc37a0fd9388e28d06f516a89
|
||||
react-native-update: 04844fca9567508fa79649e23e7209904d9d7a5a
|
||||
react-native-update: a7f136a3c87183b13c7ff5c4f9d2b614930968ad
|
||||
React-perflogger: ad1416a715d86b32f456e5d0aed99c3b52f1de37
|
||||
React-RCTActionSheet: cbf7c6a953982562418ee72a1084ff7b9447b558
|
||||
React-RCTAnimation: 33df3e25824dd7313edec28dded2745542f9352b
|
||||
@@ -457,6 +462,7 @@ SPEC CHECKSUMS:
|
||||
React-RCTVibration: 5462287ee85304ba1a00474665ab292e63a41663
|
||||
React-runtimeexecutor: 9df680f18497367bcf5c15b6b6406c0f2dfa2b6a
|
||||
ReactCommon: c10f046f3ef8561e7c8e7e9b9dae2ecc9ffc48ef
|
||||
ReactNativeCameraKit: 4bec78d688adcd68772af2834d5c30a6a8e2a384
|
||||
RNVectorIcons: bc7ee28cadf39c77a49232a14738dfce690f66cd
|
||||
SSZipArchive: fe6a26b2a54d5a0890f2567b5cc6de5caa600aef
|
||||
Yoga: d3820731e0ca3a4933f061ad29defaf7726e3251
|
||||
|
@@ -9,16 +9,18 @@
|
||||
"test": "jest",
|
||||
"test:e2e": "detox test --configuration android.emu.debug",
|
||||
"lint": "eslint .",
|
||||
"postinstall": "patch-package"
|
||||
"postinstall": "patch-package",
|
||||
"apk": "cd android && ./gradlew assembleRelease"
|
||||
},
|
||||
"dependencies": {
|
||||
"patch-package": "^6.5.1",
|
||||
"postinstall-postinstall": "^2.1.0",
|
||||
"react": "18.0.0",
|
||||
"react-native": "0.69.8",
|
||||
"react-native-camera-kit": "^14.0.0-beta15",
|
||||
"react-native-paper": "^5.12.1",
|
||||
"react-native-safe-area-context": "^4.8.2",
|
||||
"react-native-update": "^10.7.1",
|
||||
"react-native-update": "^10.11.3",
|
||||
"react-native-vector-icons": "^10.0.3"
|
||||
},
|
||||
"devDependencies": {
|
||||
|
@@ -1,6 +1,6 @@
|
||||
/* eslint-disable react/no-unstable-nested-components */
|
||||
/* eslint-disable react-native/no-inline-styles */
|
||||
import React, {useState} from 'react';
|
||||
import React, {useRef, useState} from 'react';
|
||||
import {
|
||||
StyleSheet,
|
||||
Platform,
|
||||
@@ -10,7 +10,16 @@ import {
|
||||
Image,
|
||||
Switch,
|
||||
} from 'react-native';
|
||||
import {Icon, PaperProvider, Snackbar, Banner} from 'react-native-paper';
|
||||
import {
|
||||
Icon,
|
||||
PaperProvider,
|
||||
Snackbar,
|
||||
Banner,
|
||||
Button,
|
||||
Modal,
|
||||
Portal,
|
||||
} from 'react-native-paper';
|
||||
import {Camera} from 'react-native-camera-kit';
|
||||
|
||||
import TestConsole from './TestConsole';
|
||||
|
||||
@@ -28,6 +37,7 @@ function App() {
|
||||
updateInfo,
|
||||
packageVersion,
|
||||
currentHash,
|
||||
parseTestQrCode,
|
||||
progress: {received, total} = {},
|
||||
} = usePushy();
|
||||
const [useDefaultAlert, setUseDefaultAlert] = useState(true);
|
||||
@@ -36,6 +46,8 @@ function App() {
|
||||
const [showUpdateSnackbar, setShowUpdateSnackbar] = useState(false);
|
||||
const snackbarVisible =
|
||||
!useDefaultAlert && showUpdateSnackbar && updateInfo?.update;
|
||||
const [showCamera, setShowCamera] = useState(false);
|
||||
const lastParsedCode = useRef('');
|
||||
|
||||
return (
|
||||
<View style={styles.container}>
|
||||
@@ -55,6 +67,30 @@ function App() {
|
||||
}}
|
||||
/>
|
||||
</View>
|
||||
<Button onPress={() => setShowCamera(true)}>打开相机</Button>
|
||||
<Portal>
|
||||
<Modal visible={showCamera} onDismiss={() => setShowCamera(false)}>
|
||||
<Camera
|
||||
style={{minHeight: 320}}
|
||||
scanBarcode={true}
|
||||
onReadCode={({nativeEvent: {codeStringValue}}) => {
|
||||
// 防止重复扫码
|
||||
if (lastParsedCode.current === codeStringValue) {
|
||||
return;
|
||||
}
|
||||
lastParsedCode.current = codeStringValue;
|
||||
setTimeout(() => {
|
||||
lastParsedCode.current = '';
|
||||
}, 1000);
|
||||
setShowCamera(false);
|
||||
parseTestQrCode(codeStringValue);
|
||||
}} // optional
|
||||
showFrame={true} // (default false) optional, show frame with transparent layer (qr code or barcode will be read on this area ONLY), start animation for scanner, that stops when a code has been found. Frame always at center of the screen
|
||||
laserColor="red" // (default red) optional, color of laser in scanner frame
|
||||
frameColor="white" // (default white) optional, color of border of scanner frame
|
||||
/>
|
||||
</Modal>
|
||||
</Portal>
|
||||
<Image
|
||||
resizeMode={'contain'}
|
||||
source={require('./assets/shezhi.png')}
|
||||
|
@@ -2123,7 +2123,7 @@ buffer-from@^1.0.0:
|
||||
resolved "https://registry.yarnpkg.com/buffer-from/-/buffer-from-1.1.2.tgz#2b146a6fd72e80b4f55d255f35ed59a3a9a41bd5"
|
||||
integrity sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==
|
||||
|
||||
buffer@^5.5.0:
|
||||
buffer@^5.4.3, buffer@^5.5.0:
|
||||
version "5.7.1"
|
||||
resolved "https://registry.yarnpkg.com/buffer/-/buffer-5.7.1.tgz#ba62e7c13133053582197160851a8f648e99eed0"
|
||||
integrity sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==
|
||||
@@ -6159,7 +6159,7 @@ pump@^3.0.0:
|
||||
end-of-stream "^1.1.0"
|
||||
once "^1.3.1"
|
||||
|
||||
punycode@^2.1.0:
|
||||
punycode@^2.1.0, punycode@^2.1.1:
|
||||
version "2.3.1"
|
||||
resolved "https://registry.yarnpkg.com/punycode/-/punycode-2.3.1.tgz#027422e2faec0b25e1549c3e1bd8309b9133b6e5"
|
||||
integrity sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==
|
||||
@@ -6202,6 +6202,11 @@ react-is@^17.0.1:
|
||||
resolved "https://registry.yarnpkg.com/react-is/-/react-is-17.0.2.tgz#e691d4a8e9c789365655539ab372762b0efb54f0"
|
||||
integrity sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==
|
||||
|
||||
react-native-camera-kit@^14.0.0-beta15:
|
||||
version "14.0.0-beta9"
|
||||
resolved "https://registry.yarnpkg.com/react-native-camera-kit/-/react-native-camera-kit-14.0.0-beta9.tgz#fa00aceeedd4fbc7ab82d94cb7e64de471165554"
|
||||
integrity sha512-OPRyJMmJibfVxrMvpbDgprhsrKlKWGvtLgkV+tY97HnEmTuW4in7qx/RC5wMKMZDwgBxgLtFhO7rYAMylIpH2A==
|
||||
|
||||
react-native-codegen@^0.69.2:
|
||||
version "0.69.2"
|
||||
resolved "https://registry.yarnpkg.com/react-native-codegen/-/react-native-codegen-0.69.2.tgz#e33ac3b1486de59ddae687b731ddbfcef8af0e4e"
|
||||
@@ -6231,12 +6236,20 @@ react-native-safe-area-context@^4.8.2:
|
||||
resolved "https://registry.yarnpkg.com/react-native-safe-area-context/-/react-native-safe-area-context-4.8.2.tgz#e6b3d8acf3c6afcb4b5db03a97f9c37df7668f65"
|
||||
integrity sha512-ffUOv8BJQ6RqO3nLml5gxJ6ab3EestPiyWekxdzO/1MQ7NF8fW1Mzh1C5QE9yq573Xefnc7FuzGXjtesZGv7cQ==
|
||||
|
||||
react-native-update@^10.7.1:
|
||||
version "10.7.1"
|
||||
resolved "https://registry.yarnpkg.com/react-native-update/-/react-native-update-10.7.1.tgz#f89075b69b4a397ce6d3457837018fb6cfabe0ab"
|
||||
integrity sha512-Lru/8qunNjggvjzfe6uzWi4HWsFmNjtwdLXC3lD+1hWQpJ8ln5bwQlYoXyz0n8GwNJiS8Z/w8oPXVxs323ls3g==
|
||||
react-native-update@^10.11.3:
|
||||
version "10.11.3"
|
||||
resolved "https://registry.yarnpkg.com/react-native-update/-/react-native-update-10.11.3.tgz#5fa44fdd12514eb5e7901a5d664f00fd082d6774"
|
||||
integrity sha512-adI3sly0yFt1DfaPqICJ9VwzUoa/XAngv/N7SnICkLxO3jgccBgy0OrXDBxRn43Zeumdq40Z+ADTE5qrY4BWAw==
|
||||
dependencies:
|
||||
nanoid "^3.3.3"
|
||||
react-native-url-polyfill "^2.0.0"
|
||||
|
||||
react-native-url-polyfill@^2.0.0:
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/react-native-url-polyfill/-/react-native-url-polyfill-2.0.0.tgz#db714520a2985cff1d50ab2e66279b9f91ffd589"
|
||||
integrity sha512-My330Do7/DvKnEvwQc0WdcBnFPploYKp9CYlefDXzIdEaA+PAhDYllkvGeEroEzvc4Kzzj2O4yVdz8v6fjRvhA==
|
||||
dependencies:
|
||||
whatwg-url-without-unicode "8.0.0-3"
|
||||
|
||||
react-native-vector-icons@^10.0.3:
|
||||
version "10.0.3"
|
||||
@@ -7485,11 +7498,25 @@ webidl-conversions@^3.0.0:
|
||||
resolved "https://registry.yarnpkg.com/webidl-conversions/-/webidl-conversions-3.0.1.tgz#24534275e2a7bc6be7bc86611cc16ae0a5654871"
|
||||
integrity sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==
|
||||
|
||||
webidl-conversions@^5.0.0:
|
||||
version "5.0.0"
|
||||
resolved "https://registry.yarnpkg.com/webidl-conversions/-/webidl-conversions-5.0.0.tgz#ae59c8a00b121543a2acc65c0434f57b0fc11aff"
|
||||
integrity sha512-VlZwKPCkYKxQgeSbH5EyngOmRp7Ww7I9rQLERETtf5ofd9pGeswWiOtogpEO850jziPRarreGxn5QIiTqpb2wA==
|
||||
|
||||
whatwg-fetch@^3.0.0:
|
||||
version "3.6.20"
|
||||
resolved "https://registry.yarnpkg.com/whatwg-fetch/-/whatwg-fetch-3.6.20.tgz#580ce6d791facec91d37c72890995a0b48d31c70"
|
||||
integrity sha512-EqhiFU6daOA8kpjOWTL0olhVOF3i7OrFzSYiGsEMB8GcXS+RrzauAERX65xMeNWVqxA6HXH2m69Z9LaKKdisfg==
|
||||
|
||||
whatwg-url-without-unicode@8.0.0-3:
|
||||
version "8.0.0-3"
|
||||
resolved "https://registry.yarnpkg.com/whatwg-url-without-unicode/-/whatwg-url-without-unicode-8.0.0-3.tgz#ab6df4bf6caaa6c85a59f6e82c026151d4bb376b"
|
||||
integrity sha512-HoKuzZrUlgpz35YO27XgD28uh/WJH4B0+3ttFqRo//lmq+9T/mIOJ6kqmINI9HpUpz1imRC/nR/lxKpJiv0uig==
|
||||
dependencies:
|
||||
buffer "^5.4.3"
|
||||
punycode "^2.1.1"
|
||||
webidl-conversions "^5.0.0"
|
||||
|
||||
whatwg-url@^5.0.0:
|
||||
version "5.0.0"
|
||||
resolved "https://registry.yarnpkg.com/whatwg-url/-/whatwg-url-5.0.0.tgz#966454e8765462e37644d3626f6742ce8b70965d"
|
||||
|
@@ -8,7 +8,7 @@
|
||||
|
||||
### 优势
|
||||
|
||||
1. 基于阿里云高速 CDN 分发,对比其他服务器在国外的热更新服务,分发更稳定,更新成功率极高。
|
||||
1. 对中国用户使用阿里云高速 CDN 分发,对比其他服务器在国外的热更新服务,分发更稳定,更新成功率极高。对国外用户则智能分流至 cloudflare,同样享受高速更新服务。
|
||||
2. 基于 bsdiff/hdiff 算法创建的**超小更新包**,通常版本迭代后在几十 KB 级别(其他全量热更新服务所需流量通常在几十 MB 级别)。
|
||||
3. 始终跟进 RN 最新正式版本,第一时间提供支持。支持 hermes 字节码格式。支持新架构。
|
||||
4. 跨越多个版本进行更新时,只需要下载**一个更新包**,不需要逐版本依次更新。
|
||||
@@ -33,4 +33,3 @@ $ yarn start
|
||||
本组件由[React Native 中文网](https://reactnative.cn/)独家发布,如有定制需求可以[联系我们](https://reactnative.cn/about.html#content)。
|
||||
|
||||
关于此插件发现任何问题,可以前往[Issues](https://github.com/reactnativecn/react-native-pushy/issues)发帖提问。
|
||||
|
||||
|
@@ -1 +1 @@
|
||||
["https://update.react-native.cn/api", "https://update.reactnative.cn/api", "https://p.reactnative.cn/api"]
|
||||
["https://pushy-koa-qgbgqmcpis.cn-beijing.fcapp.run", "https://p.reactnative.cn/api"]
|
||||
|
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "react-native-update",
|
||||
"version": "10.9.0",
|
||||
"version": "10.11.5",
|
||||
"description": "react-native hot update",
|
||||
"main": "src/index",
|
||||
"scripts": {
|
||||
@@ -45,7 +45,8 @@
|
||||
},
|
||||
"homepage": "https://github.com/reactnativecn/react-native-pushy#readme",
|
||||
"dependencies": {
|
||||
"nanoid": "^3.3.3"
|
||||
"nanoid": "^3.3.3",
|
||||
"react-native-url-polyfill": "^2.0.0"
|
||||
},
|
||||
"codegenConfig": {
|
||||
"name": "RCTPushySpec",
|
||||
|
@@ -17,8 +17,10 @@ import {
|
||||
const defaultServer = {
|
||||
main: 'https://update.react-native.cn/api',
|
||||
backups: ['https://update.reactnative.cn/api'],
|
||||
queryUrl:
|
||||
queryUrls: [
|
||||
'https://gitee.com/sunnylqm/react-native-pushy/raw/master/endpoints.json',
|
||||
'https://cdn.jsdelivr.net/gh/reactnativecn/react-native-pushy@master/endpoints.json',
|
||||
],
|
||||
};
|
||||
|
||||
const empty = {};
|
||||
@@ -170,7 +172,6 @@ export class Pushy {
|
||||
return await this.lastRespJson;
|
||||
}
|
||||
this.lastChecking = now;
|
||||
this.report({ type: 'checking' });
|
||||
const fetchBody = {
|
||||
packageVersion,
|
||||
hash: currentVersion,
|
||||
@@ -181,16 +182,21 @@ export class Pushy {
|
||||
if (__DEV__) {
|
||||
delete fetchBody.buildTime;
|
||||
}
|
||||
const body = JSON.stringify(fetchBody);
|
||||
const fetchPayload = {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
Accept: 'application/json',
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
body: JSON.stringify(fetchBody),
|
||||
body,
|
||||
};
|
||||
let resp;
|
||||
try {
|
||||
this.report({
|
||||
type: 'checking',
|
||||
message: this.options.appKey + ': ' + body,
|
||||
});
|
||||
resp = await fetch(this.getCheckUrl(), fetchPayload);
|
||||
} catch (e: any) {
|
||||
this.report({
|
||||
@@ -219,6 +225,8 @@ export class Pushy {
|
||||
|
||||
const result: CheckResult = await this.lastRespJson;
|
||||
|
||||
log('checking result:', result);
|
||||
|
||||
if (resp.status !== 200) {
|
||||
this.report({
|
||||
type: 'errorChecking',
|
||||
@@ -233,9 +241,11 @@ export class Pushy {
|
||||
if (!server) {
|
||||
return [];
|
||||
}
|
||||
if (server.queryUrl) {
|
||||
if (server.queryUrls) {
|
||||
try {
|
||||
const resp = await fetch(server.queryUrl);
|
||||
const resp = await Promise.race(
|
||||
server.queryUrls.map(queryUrl => fetch(queryUrl)),
|
||||
);
|
||||
const remoteEndpoints = await resp.json();
|
||||
log('fetch endpoints:', remoteEndpoints);
|
||||
if (Array.isArray(remoteEndpoints)) {
|
||||
@@ -244,7 +254,7 @@ export class Pushy {
|
||||
);
|
||||
}
|
||||
} catch (e: any) {
|
||||
log('failed to fetch endpoints from: ', server.queryUrl);
|
||||
log('failed to fetch endpoints from: ', server.queryUrls);
|
||||
}
|
||||
}
|
||||
return server.backups;
|
||||
@@ -289,7 +299,7 @@ export class Pushy {
|
||||
},
|
||||
);
|
||||
}
|
||||
let succeeded = false;
|
||||
let succeeded = '';
|
||||
this.report({ type: 'downloading' });
|
||||
let lastError: any;
|
||||
const diffUrl = (await testUrls(diffUrls)) || _diffUrl;
|
||||
@@ -301,11 +311,11 @@ export class Pushy {
|
||||
hash,
|
||||
originHash: currentVersion,
|
||||
});
|
||||
succeeded = true;
|
||||
succeeded = 'diff';
|
||||
} catch (e: any) {
|
||||
lastError = e;
|
||||
if (__DEV__) {
|
||||
succeeded = true;
|
||||
succeeded = 'diff';
|
||||
} else {
|
||||
log(`diff error: ${e.message}, try pdiff`);
|
||||
}
|
||||
@@ -319,11 +329,11 @@ export class Pushy {
|
||||
updateUrl: pdiffUrl,
|
||||
hash,
|
||||
});
|
||||
succeeded = true;
|
||||
succeeded = 'pdiff';
|
||||
} catch (e: any) {
|
||||
lastError = e;
|
||||
if (__DEV__) {
|
||||
succeeded = true;
|
||||
succeeded = 'pdiff';
|
||||
} else {
|
||||
log(`pdiff error: ${e.message}, try full patch`);
|
||||
}
|
||||
@@ -337,11 +347,11 @@ export class Pushy {
|
||||
updateUrl: updateUrl,
|
||||
hash,
|
||||
});
|
||||
succeeded = true;
|
||||
succeeded = 'full';
|
||||
} catch (e: any) {
|
||||
lastError = e;
|
||||
if (__DEV__) {
|
||||
succeeded = true;
|
||||
succeeded = 'full';
|
||||
} else {
|
||||
log(`full patch error: ${e.message}`);
|
||||
}
|
||||
@@ -363,8 +373,13 @@ export class Pushy {
|
||||
throw lastError;
|
||||
}
|
||||
return;
|
||||
} else {
|
||||
this.report({
|
||||
type: 'downloadSuccess',
|
||||
data: { newVersion: hash, diff: succeeded },
|
||||
});
|
||||
}
|
||||
log('downloaded hash:', hash);
|
||||
log(`downloaded ${succeeded} hash:`, hash);
|
||||
setLocalHashInfo(hash, {
|
||||
name,
|
||||
description,
|
||||
|
@@ -14,6 +14,7 @@ export const defaultContext = {
|
||||
downloadUpdate: asyncNoop,
|
||||
downloadAndInstallApk: asyncNoop,
|
||||
getCurrentVersionInfo: () => Promise.resolve({}),
|
||||
parseTestQrCode: () => false,
|
||||
currentHash: '',
|
||||
packageVersion: '',
|
||||
};
|
||||
@@ -31,6 +32,7 @@ export const PushyContext = createContext<{
|
||||
description?: string;
|
||||
metaInfo?: string;
|
||||
}>;
|
||||
parseTestQrCode: (code: string) => boolean;
|
||||
currentHash: string;
|
||||
packageVersion: string;
|
||||
client?: Pushy;
|
||||
|
@@ -19,8 +19,9 @@ import {
|
||||
packageVersion,
|
||||
getCurrentVersionInfo,
|
||||
} from './core';
|
||||
import { CheckResult, ProgressData } from './type';
|
||||
import { CheckResult, ProgressData, PushyTestPayload } from './type';
|
||||
import { PushyContext } from './context';
|
||||
import { URL } from 'react-native-url-polyfill';
|
||||
|
||||
export const PushyProvider = ({
|
||||
client,
|
||||
@@ -146,7 +147,7 @@ export const PushyProvider = ({
|
||||
);
|
||||
|
||||
const checkUpdate = useCallback(
|
||||
async (extra?: Record<string, any>) => {
|
||||
async ({ extra }: { extra?: Record<string, any> } | undefined = {}) => {
|
||||
const now = Date.now();
|
||||
if (lastChecking.current && now - lastChecking.current < 1000) {
|
||||
return;
|
||||
@@ -262,6 +263,66 @@ export const PushyProvider = ({
|
||||
};
|
||||
}, [checkUpdate, options, dismissError, markSuccess]);
|
||||
|
||||
const parseTestPayload = useCallback(
|
||||
(payload: PushyTestPayload) => {
|
||||
if (payload && payload.type && payload.type.startsWith('__rnPushy')) {
|
||||
const logger = options.logger || (() => {});
|
||||
options.logger = ({ type, data }) => {
|
||||
logger({ type, data });
|
||||
Alert.alert(type, JSON.stringify(data));
|
||||
};
|
||||
if (payload.type === '__rnPushyVersionHash') {
|
||||
checkUpdate({ extra: { toHash: payload.data } }).then(() => {
|
||||
if (updateInfoRef.current && updateInfoRef.current.upToDate) {
|
||||
Alert.alert(
|
||||
'提示',
|
||||
'当前尚未检测到更新版本,如果是首次扫码,请等待服务器端生成补丁包后再试(约10秒)',
|
||||
);
|
||||
}
|
||||
options.logger = logger;
|
||||
});
|
||||
}
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
},
|
||||
[checkUpdate, options],
|
||||
);
|
||||
|
||||
const parseTestQrCode = useCallback(
|
||||
(code: string | PushyTestPayload) => {
|
||||
try {
|
||||
const payload = typeof code === 'string' ? JSON.parse(code) : code;
|
||||
return parseTestPayload(payload);
|
||||
} catch {
|
||||
return false;
|
||||
}
|
||||
},
|
||||
[parseTestPayload],
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
const parseLinking = (url: string | null) => {
|
||||
if (!url) {
|
||||
return;
|
||||
}
|
||||
const params = new URL(url).searchParams;
|
||||
const payload = {
|
||||
type: params.get('type'),
|
||||
data: params.get('data'),
|
||||
};
|
||||
parseTestPayload(payload);
|
||||
};
|
||||
|
||||
Linking.getInitialURL().then(parseLinking);
|
||||
const linkingListener = Linking.addEventListener('url', ({ url }) =>
|
||||
parseLinking(url),
|
||||
);
|
||||
return () => {
|
||||
linkingListener.remove();
|
||||
};
|
||||
}, [parseTestPayload]);
|
||||
|
||||
return (
|
||||
<PushyContext.Provider
|
||||
value={{
|
||||
@@ -279,6 +340,7 @@ export const PushyProvider = ({
|
||||
progress,
|
||||
downloadAndInstallApk,
|
||||
getCurrentVersionInfo,
|
||||
parseTestQrCode,
|
||||
}}>
|
||||
{children}
|
||||
</PushyContext.Provider>
|
||||
|
@@ -28,6 +28,7 @@ export type EventType =
|
||||
| 'errorChecking'
|
||||
| 'checking'
|
||||
| 'downloading'
|
||||
| 'downloadSuccess'
|
||||
| 'errorUpdate'
|
||||
| 'markSuccess'
|
||||
| 'downloadingApk'
|
||||
@@ -62,7 +63,7 @@ export type UpdateEventsLogger = ({
|
||||
export interface PushyServerConfig {
|
||||
main: string;
|
||||
backups?: string[];
|
||||
queryUrl?: string;
|
||||
queryUrls?: string[];
|
||||
}
|
||||
|
||||
export interface PushyOptions {
|
||||
@@ -81,3 +82,8 @@ export interface PushyOptions {
|
||||
debug?: boolean;
|
||||
throwError?: boolean;
|
||||
}
|
||||
|
||||
export interface PushyTestPayload {
|
||||
type: '__rnPushyVersionHash' | string | null;
|
||||
data: any;
|
||||
}
|
||||
|
23
yarn.lock
23
yarn.lock
@@ -3198,7 +3198,7 @@ buffer-indexof-polyfill@~1.0.0:
|
||||
resolved "https://registry.npmjs.org/buffer-indexof-polyfill/-/buffer-indexof-polyfill-1.0.2.tgz#d2732135c5999c64b277fcf9b1abe3498254729c"
|
||||
integrity sha512-I7wzHwA3t1/lwXQh+A5PbNvJxgfo5r3xulgpYDB5zckTu/Z9oUK9biouBKQUjEqzaz3HnAT6TYoovmE+GqSf7A==
|
||||
|
||||
buffer@^5.5.0:
|
||||
buffer@^5.4.3, buffer@^5.5.0:
|
||||
version "5.7.1"
|
||||
resolved "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz#ba62e7c13133053582197160851a8f648e99eed0"
|
||||
integrity sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==
|
||||
@@ -8604,6 +8604,13 @@ react-is@^17.0.1:
|
||||
resolved "https://registry.yarnpkg.com/react-is/-/react-is-17.0.2.tgz#e691d4a8e9c789365655539ab372762b0efb54f0"
|
||||
integrity sha512-w2GsyukL62IJnlaff/nRegPQR94C/XXamvMWmSHRJ4y7Ts/4ocGRmTHvOs8PSE6pB3dWOrD/nueuU5sduBsQ4w==
|
||||
|
||||
react-native-url-polyfill@^2.0.0:
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/react-native-url-polyfill/-/react-native-url-polyfill-2.0.0.tgz#db714520a2985cff1d50ab2e66279b9f91ffd589"
|
||||
integrity sha512-My330Do7/DvKnEvwQc0WdcBnFPploYKp9CYlefDXzIdEaA+PAhDYllkvGeEroEzvc4Kzzj2O4yVdz8v6fjRvhA==
|
||||
dependencies:
|
||||
whatwg-url-without-unicode "8.0.0-3"
|
||||
|
||||
react-native@0.73:
|
||||
version "0.73.2"
|
||||
resolved "https://registry.yarnpkg.com/react-native/-/react-native-0.73.2.tgz#74ee163c8189660d41d1da6560411da7ce41a608"
|
||||
@@ -10174,6 +10181,11 @@ webidl-conversions@^3.0.0:
|
||||
resolved "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz#24534275e2a7bc6be7bc86611cc16ae0a5654871"
|
||||
integrity sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==
|
||||
|
||||
webidl-conversions@^5.0.0:
|
||||
version "5.0.0"
|
||||
resolved "https://registry.yarnpkg.com/webidl-conversions/-/webidl-conversions-5.0.0.tgz#ae59c8a00b121543a2acc65c0434f57b0fc11aff"
|
||||
integrity sha512-VlZwKPCkYKxQgeSbH5EyngOmRp7Ww7I9rQLERETtf5ofd9pGeswWiOtogpEO850jziPRarreGxn5QIiTqpb2wA==
|
||||
|
||||
whatwg-fetch@^3.0.0:
|
||||
version "3.6.19"
|
||||
resolved "https://registry.yarnpkg.com/whatwg-fetch/-/whatwg-fetch-3.6.19.tgz#caefd92ae630b91c07345537e67f8354db470973"
|
||||
@@ -10184,6 +10196,15 @@ whatwg-fetch@^3.4.1:
|
||||
resolved "https://registry.npmjs.org/whatwg-fetch/-/whatwg-fetch-3.6.2.tgz#dced24f37f2624ed0281725d51d0e2e3fe677f8c"
|
||||
integrity sha512-bJlen0FcuU/0EMLrdbJ7zOnW6ITZLrZMIarMUVmdKtsGvZna8vxKYaexICWPfZ8qwf9fzNq+UEIZrnSaApt6RA==
|
||||
|
||||
whatwg-url-without-unicode@8.0.0-3:
|
||||
version "8.0.0-3"
|
||||
resolved "https://registry.yarnpkg.com/whatwg-url-without-unicode/-/whatwg-url-without-unicode-8.0.0-3.tgz#ab6df4bf6caaa6c85a59f6e82c026151d4bb376b"
|
||||
integrity sha512-HoKuzZrUlgpz35YO27XgD28uh/WJH4B0+3ttFqRo//lmq+9T/mIOJ6kqmINI9HpUpz1imRC/nR/lxKpJiv0uig==
|
||||
dependencies:
|
||||
buffer "^5.4.3"
|
||||
punycode "^2.1.1"
|
||||
webidl-conversions "^5.0.0"
|
||||
|
||||
whatwg-url@^5.0.0:
|
||||
version "5.0.0"
|
||||
resolved "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz#966454e8765462e37644d3626f6742ce8b70965d"
|
||||
|
Reference in New Issue
Block a user