mirror of
https://gitcode.com/gh_mirrors/re/react-native-pushy.git
synced 2025-10-23 09:38:52 +08:00
support multiple versions
This commit is contained in:
@@ -91,7 +91,8 @@ export class Pushy {
|
||||
options = defaultClientOptions;
|
||||
clientType: 'Pushy' | 'Cresc' = 'Pushy';
|
||||
lastChecking?: number;
|
||||
lastRespJson?: Promise<any>;
|
||||
lastRespJson?: Promise<CheckResult>;
|
||||
lastRespText?: Promise<string>;
|
||||
|
||||
version = cInfo.rnu;
|
||||
loggerPromise = (() => {
|
||||
@@ -294,20 +295,23 @@ export class Pushy {
|
||||
this.throwIfEnabled(new Error('errorChecking'));
|
||||
return this.lastRespJson ? await this.lastRespJson : emptyObj;
|
||||
}
|
||||
|
||||
if (resp.status !== 200) {
|
||||
const errorMessage = `${resp.status}: ${resp.statusText}`;
|
||||
this.report({
|
||||
type: 'errorChecking',
|
||||
message: errorMessage,
|
||||
});
|
||||
this.throwIfEnabled(new Error(errorMessage));
|
||||
log('error checking response:', resp.status, await resp.text());
|
||||
return this.lastRespJson ? await this.lastRespJson : emptyObj;
|
||||
}
|
||||
this.lastRespJson = resp.json();
|
||||
|
||||
const result: CheckResult = await this.lastRespJson;
|
||||
|
||||
log('checking result:', result);
|
||||
|
||||
if (resp.status !== 200) {
|
||||
this.report({
|
||||
type: 'errorChecking',
|
||||
message: result.message,
|
||||
});
|
||||
this.throwIfEnabled(new Error(result.message));
|
||||
}
|
||||
|
||||
return result;
|
||||
};
|
||||
getBackupEndpoints = async () => {
|
||||
|
142
src/provider.tsx
142
src/provider.tsx
@@ -14,7 +14,12 @@ import {
|
||||
} from 'react-native';
|
||||
import { Pushy, Cresc, sharedState } from './client';
|
||||
import { currentVersion, packageVersion, getCurrentVersionInfo } from './core';
|
||||
import { CheckResult, ProgressData, UpdateTestPayload } from './type';
|
||||
import {
|
||||
CheckResult,
|
||||
MixedCheckResult,
|
||||
ProgressData,
|
||||
UpdateTestPayload,
|
||||
} from './type';
|
||||
import { UpdateContext } from './context';
|
||||
import { URL } from 'react-native-url-polyfill';
|
||||
import { isInRollout } from './isInRollout';
|
||||
@@ -158,84 +163,95 @@ export const UpdateProvider = ({
|
||||
return;
|
||||
}
|
||||
lastChecking.current = now;
|
||||
let info: CheckResult;
|
||||
let rootInfo: MixedCheckResult | undefined;
|
||||
try {
|
||||
info = await client.checkUpdate(extra);
|
||||
rootInfo = await client.checkUpdate(extra);
|
||||
} catch (e: any) {
|
||||
setLastError(e);
|
||||
alertError('更新检查失败', e.message);
|
||||
throwErrorIfEnabled(e);
|
||||
return;
|
||||
}
|
||||
if (!info) {
|
||||
if (!rootInfo) {
|
||||
return;
|
||||
}
|
||||
const rollout = info.config?.rollout?.[packageVersion];
|
||||
if (info.update && rollout) {
|
||||
if (!isInRollout(rollout)) {
|
||||
log(`not in ${rollout}% rollout, ignored`);
|
||||
return;
|
||||
const versions = rootInfo.versions || [rootInfo as CheckResult];
|
||||
delete rootInfo.versions;
|
||||
for (const versionInfo of versions) {
|
||||
const info: CheckResult = {
|
||||
...versionInfo,
|
||||
...rootInfo,
|
||||
};
|
||||
const rollout = info.config?.rollout?.[packageVersion];
|
||||
if (info.update && rollout) {
|
||||
if (!isInRollout(rollout)) {
|
||||
log(`${info.name} not in ${rollout}% rollout, ignored`);
|
||||
continue;
|
||||
}
|
||||
log(`${info.name} in ${rollout}% rollout, continue`);
|
||||
}
|
||||
log(`in ${rollout}% rollout, continue`);
|
||||
}
|
||||
info.description = info.description ?? '';
|
||||
updateInfoRef.current = info;
|
||||
setUpdateInfo(info);
|
||||
if (info.expired) {
|
||||
if (
|
||||
options.onPackageExpired &&
|
||||
(await options.onPackageExpired(info)) === false
|
||||
) {
|
||||
log('onPackageExpired returned false, skipping');
|
||||
return;
|
||||
}
|
||||
const { downloadUrl } = info;
|
||||
if (downloadUrl && sharedState.apkStatus === null) {
|
||||
if (options.updateStrategy === 'silentAndNow') {
|
||||
if (Platform.OS === 'android' && downloadUrl.endsWith('.apk')) {
|
||||
downloadAndInstallApk(downloadUrl);
|
||||
} else {
|
||||
Linking.openURL(downloadUrl);
|
||||
info.description = info.description ?? '';
|
||||
updateInfoRef.current = info;
|
||||
setUpdateInfo(info);
|
||||
if (info.expired) {
|
||||
if (
|
||||
options.onPackageExpired &&
|
||||
(await options.onPackageExpired(info)) === false
|
||||
) {
|
||||
log('onPackageExpired returned false, skipping');
|
||||
return;
|
||||
}
|
||||
const { downloadUrl } = info;
|
||||
if (downloadUrl && sharedState.apkStatus === null) {
|
||||
if (options.updateStrategy === 'silentAndNow') {
|
||||
if (Platform.OS === 'android' && downloadUrl.endsWith('.apk')) {
|
||||
downloadAndInstallApk(downloadUrl);
|
||||
} else {
|
||||
Linking.openURL(downloadUrl);
|
||||
}
|
||||
return info;
|
||||
}
|
||||
alertUpdate('提示', '您的应用版本已更新,点击更新下载安装新版本', [
|
||||
{
|
||||
text: '更新',
|
||||
onPress: () => {
|
||||
if (
|
||||
Platform.OS === 'android' &&
|
||||
downloadUrl.endsWith('.apk')
|
||||
) {
|
||||
downloadAndInstallApk(downloadUrl);
|
||||
} else {
|
||||
Linking.openURL(downloadUrl);
|
||||
}
|
||||
},
|
||||
},
|
||||
]);
|
||||
}
|
||||
} else if (info.update) {
|
||||
if (
|
||||
options.updateStrategy === 'silentAndNow' ||
|
||||
options.updateStrategy === 'silentAndLater'
|
||||
) {
|
||||
downloadUpdate(info);
|
||||
return info;
|
||||
}
|
||||
alertUpdate('提示', '您的应用版本已更新,点击更新下载安装新版本', [
|
||||
{
|
||||
text: '更新',
|
||||
onPress: () => {
|
||||
if (Platform.OS === 'android' && downloadUrl.endsWith('.apk')) {
|
||||
downloadAndInstallApk(downloadUrl);
|
||||
} else {
|
||||
Linking.openURL(downloadUrl);
|
||||
}
|
||||
alertUpdate(
|
||||
'提示',
|
||||
'检查到新的版本' + info.name + ',是否下载?\n' + info.description,
|
||||
[
|
||||
{ text: '取消', style: 'cancel' },
|
||||
{
|
||||
text: '确定',
|
||||
style: 'default',
|
||||
onPress: () => {
|
||||
downloadUpdate();
|
||||
},
|
||||
},
|
||||
},
|
||||
]);
|
||||
],
|
||||
);
|
||||
}
|
||||
} else if (info.update) {
|
||||
if (
|
||||
options.updateStrategy === 'silentAndNow' ||
|
||||
options.updateStrategy === 'silentAndLater'
|
||||
) {
|
||||
downloadUpdate(info);
|
||||
return info;
|
||||
}
|
||||
alertUpdate(
|
||||
'提示',
|
||||
'检查到新的版本' + info.name + ',是否下载?\n' + info.description,
|
||||
[
|
||||
{ text: '取消', style: 'cancel' },
|
||||
{
|
||||
text: '确定',
|
||||
style: 'default',
|
||||
onPress: () => {
|
||||
downloadUpdate();
|
||||
},
|
||||
},
|
||||
],
|
||||
);
|
||||
return info;
|
||||
}
|
||||
return info;
|
||||
},
|
||||
[
|
||||
client,
|
||||
|
36
src/type.ts
36
src/type.ts
@@ -1,14 +1,10 @@
|
||||
export interface CheckResult {
|
||||
upToDate?: true;
|
||||
expired?: true;
|
||||
downloadUrl?: string;
|
||||
update?: true;
|
||||
name?: string; // version name
|
||||
hash?: string;
|
||||
description?: string;
|
||||
metaInfo?: string;
|
||||
config?: {
|
||||
rollout?: {
|
||||
export interface VersionInfo {
|
||||
name: string;
|
||||
hash: string;
|
||||
description: string;
|
||||
metaInfo: string;
|
||||
config: {
|
||||
rollout: {
|
||||
[packageVersion: string]: number;
|
||||
};
|
||||
[key: string]: any;
|
||||
@@ -16,11 +12,27 @@ export interface CheckResult {
|
||||
pdiff?: string;
|
||||
diff?: string;
|
||||
full?: string;
|
||||
paths?: string[];
|
||||
}
|
||||
|
||||
interface RootResult {
|
||||
upToDate?: true;
|
||||
expired?: true;
|
||||
downloadUrl?: string;
|
||||
update?: true;
|
||||
paused?: 'app' | 'package';
|
||||
message?: string;
|
||||
paths?: string[];
|
||||
}
|
||||
|
||||
export type CheckResult = RootResult & VersionInfo;
|
||||
|
||||
export type CheckResultV2 = RootResult & {
|
||||
versions?: VersionInfo[];
|
||||
};
|
||||
|
||||
export type MixedCheckResult = CheckResult | CheckResultV2;
|
||||
|
||||
|
||||
export interface ProgressData {
|
||||
hash: string;
|
||||
received: number;
|
||||
|
Reference in New Issue
Block a user