Skip to content
This repository was archived by the owner on May 20, 2025. It is now read-only.

Commit 3086aea

Browse files
committed
iOS implementation of getUpdateMetadata
1 parent bd09373 commit 3086aea

File tree

6 files changed

+94
-53
lines changed

6 files changed

+94
-53
lines changed

CodePush.js

Lines changed: 17 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -100,12 +100,16 @@ const getConfiguration = (() => {
100100
})();
101101

102102
async function getCurrentPackage() {
103-
const localPackage = await NativeCodePush.getCurrentPackage();
104-
if (localPackage) {
105-
localPackage.failedInstall = await NativeCodePush.isFailedUpdate(localPackage.packageHash);
106-
localPackage.isFirstRun = await NativeCodePush.isFirstRun(localPackage.packageHash);
103+
return await getUpdateMetadata(CodePush.UpdateState.LATEST);
104+
}
105+
106+
async function getUpdateMetadata(updateState) {
107+
const updateMetadata = await NativeCodePush.getUpdateMetadata(updateState || CodePush.UpdateState.RUNNING);
108+
if (updateMetadata) {
109+
updateMetadata.failedInstall = await NativeCodePush.isFailedUpdate(updateMetadata.packageHash);
110+
updateMetadata.isFirstRun = await NativeCodePush.isFirstRun(updateMetadata.packageHash);
107111
}
108-
return localPackage;
112+
return updateMetadata;
109113
}
110114

111115
function getPromisifiedSdk(requestFetchAdapter, config) {
@@ -388,9 +392,11 @@ if (NativeCodePush) {
388392
checkForUpdate,
389393
getConfiguration,
390394
getCurrentPackage,
395+
getUpdateMetadata,
391396
log,
392397
notifyApplicationReady,
393398
restartApp,
399+
restartApplication: restartApp,
394400
setUpTestDependencies,
395401
sync,
396402
InstallMode: {
@@ -409,6 +415,11 @@ if (NativeCodePush) {
409415
SYNC_IN_PROGRESS: 7, // There is an ongoing "sync" operation in progress.
410416
UNKNOWN_ERROR: -1
411417
},
418+
UpdateState: {
419+
RUNNING: NativeCodePush.codePushUpdateStateRunning,
420+
PENDING: NativeCodePush.codePushUpdateStatePending,
421+
LATEST: NativeCodePush.codePushUpdateStateLatest
422+
},
412423
DEFAULT_UPDATE_DIALOG: {
413424
appendReleaseDescription: false,
414425
descriptionPrefix: " Description: ",
@@ -424,4 +435,4 @@ if (NativeCodePush) {
424435
log("The CodePush module doesn't appear to be properly installed. Please double-check that everything is setup correctly.");
425436
}
426437

427-
module.exports = CodePush;
438+
module.exports = CodePush;

ios/CodePush.xcodeproj/project.pbxproj

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
13BE3DEE1AC21097009241FE /* CodePush.m in Sources */ = {isa = PBXBuildFile; fileRef = 13BE3DED1AC21097009241FE /* CodePush.m */; };
1111
1B23B9141BF9267B000BB2F0 /* RCTConvert+CodePushInstallMode.m in Sources */ = {isa = PBXBuildFile; fileRef = 1B23B9131BF9267B000BB2F0 /* RCTConvert+CodePushInstallMode.m */; };
1212
1B762E901C9A5E9A006EF800 /* CodePushErrorUtils.m in Sources */ = {isa = PBXBuildFile; fileRef = 1B762E8F1C9A5E9A006EF800 /* CodePushErrorUtils.m */; };
13+
1BCC09A71CC19EB700DDC0DD /* RCTConvert+CodePushUpdateState.m in Sources */ = {isa = PBXBuildFile; fileRef = 1BCC09A61CC19EB700DDC0DD /* RCTConvert+CodePushUpdateState.m */; };
1314
540D20121C7684FE00D6EF41 /* CodePushUpdateUtils.m in Sources */ = {isa = PBXBuildFile; fileRef = 540D20111C7684FE00D6EF41 /* CodePushUpdateUtils.m */; };
1415
5421FE311C58AD5A00986A55 /* CodePushTelemetryManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 5421FE301C58AD5A00986A55 /* CodePushTelemetryManager.m */; };
1516
54A0026C1C0E2880004C3CEC /* aescrypt.c in Sources */ = {isa = PBXBuildFile; fileRef = 54A0024C1C0E2880004C3CEC /* aescrypt.c */; };
@@ -49,6 +50,7 @@
4950
13BE3DED1AC21097009241FE /* CodePush.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = CodePush.m; path = CodePush/CodePush.m; sourceTree = "<group>"; };
5051
1B23B9131BF9267B000BB2F0 /* RCTConvert+CodePushInstallMode.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = "RCTConvert+CodePushInstallMode.m"; path = "CodePush/RCTConvert+CodePushInstallMode.m"; sourceTree = "<group>"; };
5152
1B762E8F1C9A5E9A006EF800 /* CodePushErrorUtils.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = CodePushErrorUtils.m; path = CodePush/CodePushErrorUtils.m; sourceTree = "<group>"; };
53+
1BCC09A61CC19EB700DDC0DD /* RCTConvert+CodePushUpdateState.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = "RCTConvert+CodePushUpdateState.m"; path = "CodePush/RCTConvert+CodePushUpdateState.m"; sourceTree = "<group>"; };
5254
540D20111C7684FE00D6EF41 /* CodePushUpdateUtils.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = CodePushUpdateUtils.m; path = CodePush/CodePushUpdateUtils.m; sourceTree = "<group>"; };
5355
5421FE301C58AD5A00986A55 /* CodePushTelemetryManager.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = CodePushTelemetryManager.m; path = CodePush/CodePushTelemetryManager.m; sourceTree = "<group>"; };
5456
54A0024A1C0E2880004C3CEC /* aes.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = aes.h; sourceTree = "<group>"; };
@@ -168,16 +170,17 @@
168170
58B511D21A9E6C8500147676 = {
169171
isa = PBXGroup;
170172
children = (
171-
54A002481C0E2880004C3CEC /* SSZipArchive */,
172-
1B23B9131BF9267B000BB2F0 /* RCTConvert+CodePushInstallMode.m */,
173+
13BE3DEC1AC21097009241FE /* CodePush.h */,
174+
13BE3DED1AC21097009241FE /* CodePush.m */,
173175
81D51F391B6181C2000DA084 /* CodePushConfig.m */,
174176
54FFEDDF1BF550630061DD23 /* CodePushDownloadHandler.m */,
175177
1B762E8F1C9A5E9A006EF800 /* CodePushErrorUtils.m */,
176178
810D4E6C1B96935000B397E9 /* CodePushPackage.m */,
177179
5421FE301C58AD5A00986A55 /* CodePushTelemetryManager.m */,
178180
540D20111C7684FE00D6EF41 /* CodePushUpdateUtils.m */,
179-
13BE3DEC1AC21097009241FE /* CodePush.h */,
180-
13BE3DED1AC21097009241FE /* CodePush.m */,
181+
1B23B9131BF9267B000BB2F0 /* RCTConvert+CodePushInstallMode.m */,
182+
1BCC09A61CC19EB700DDC0DD /* RCTConvert+CodePushUpdateState.m */,
183+
54A002481C0E2880004C3CEC /* SSZipArchive */,
181184
134814211AA4EA7D00B7C361 /* Products */,
182185
);
183186
sourceTree = "<group>";
@@ -242,6 +245,7 @@
242245
540D20121C7684FE00D6EF41 /* CodePushUpdateUtils.m in Sources */,
243246
54A0026E1C0E2880004C3CEC /* aestab.c in Sources */,
244247
54A002761C0E2880004C3CEC /* mztools.c in Sources */,
248+
1BCC09A71CC19EB700DDC0DD /* RCTConvert+CodePushUpdateState.m in Sources */,
245249
54A002781C0E2880004C3CEC /* zip.c in Sources */,
246250
54A002791C0E2880004C3CEC /* SSZipArchive.m in Sources */,
247251
1B23B9141BF9267B000BB2F0 /* RCTConvert+CodePushInstallMode.m in Sources */,

ios/CodePush/CodePush.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,7 @@ failCallback:(void (^)(NSError *err))failCallback;
8484

8585
+ (NSString *)getBinaryAssetsPath;
8686
+ (NSDictionary *)getCurrentPackage:(NSError **)error;
87+
+ (NSDictionary *)getPreviousPackage:(NSError **)error;
8788
+ (NSString *)getCurrentPackageFolderPath:(NSError **)error;
8889
+ (NSString *)getCurrentPackageBundlePath:(NSError **)error;
8990
+ (NSString *)getCurrentPackageHash:(NSError **)error;
@@ -140,4 +141,10 @@ typedef NS_ENUM(NSInteger, CodePushInstallMode) {
140141
CodePushInstallModeImmediate,
141142
CodePushInstallModeOnNextRestart,
142143
CodePushInstallModeOnNextResume
144+
};
145+
146+
typedef NS_ENUM(NSInteger, CodePushUpdateState) {
147+
CodePushUpdateStateRunning,
148+
CodePushUpdateStatePending,
149+
CodePushUpdateStateLatest
143150
};

ios/CodePush/CodePush.m

Lines changed: 39 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -180,12 +180,16 @@ + (void)setUsingTestConfiguration:(BOOL)shouldUseTestConfiguration
180180
*/
181181
- (NSDictionary *)constantsToExport
182182
{
183-
// Export the values of the CodePushInstallMode enum
184-
// so that the script-side can easily stay in sync
183+
// Export the values of the CodePushInstallMode and CodePushUpdateState
184+
// enums so that the script-side can easily stay in sync
185185
return @{
186186
@"codePushInstallModeOnNextRestart":@(CodePushInstallModeOnNextRestart),
187187
@"codePushInstallModeImmediate": @(CodePushInstallModeImmediate),
188-
@"codePushInstallModeOnNextResume": @(CodePushInstallModeOnNextResume)
188+
@"codePushInstallModeOnNextResume": @(CodePushInstallModeOnNextResume),
189+
190+
@"codePushUpdateStateRunning": @(CodePushUpdateStateRunning),
191+
@"codePushUpdateStatePending": @(CodePushUpdateStatePending),
192+
@"codePushUpdateStateLatest": @(CodePushUpdateStateLatest)
189193
};
190194
};
191195

@@ -532,35 +536,49 @@ - (void)applicationWillResignActive
532536
}
533537

534538
/*
535-
* This method is the native side of the CodePush.getCurrentPackage method.
539+
* This method is the native side of the CodePush.getUpdateMetadata method.
536540
*/
537-
RCT_EXPORT_METHOD(getCurrentPackage:(RCTPromiseResolveBlock)resolve
541+
RCT_EXPORT_METHOD(getUpdateMetadata:(CodePushUpdateState)updateState
542+
resolver:(RCTPromiseResolveBlock)resolve
538543
rejecter:(RCTPromiseRejectBlock)reject)
539544
{
540545
NSError *error;
541546
NSMutableDictionary *package = [[CodePushPackage getCurrentPackage:&error] mutableCopy];
542547

543548
if (error) {
544-
reject([NSString stringWithFormat: @"%lu", (long)error.code], error.localizedDescription, error);
545-
return;
549+
return reject([NSString stringWithFormat: @"%lu", (long)error.code], error.localizedDescription, error);
546550
} else if (package == nil) {
547-
resolve(nil);
548-
return;
551+
// The app hasn't downloaded any CodePush updates yet,
552+
// so we simply return nil regardless if the user
553+
// wanted to retrieve the pending or running update.
554+
return resolve(nil);
549555
}
550556

551-
if (isRunningBinaryVersion) {
552-
// This only matters in Debug builds. Since we do not clear "outdated" updates,
553-
// we need to indicate to the JS side that somehow we have a current update on
554-
// disk that is not actually running.
555-
[package setObject:@(YES) forKey:@"_isDebugOnly"];
557+
// We have a CodePush update, so let's see if it's currently in a pending state.
558+
BOOL currentUpdateIsPending = [self isPendingUpdate:[package objectForKey:PackageHashKey]];
559+
560+
if (updateState == CodePushUpdateStatePending && !currentUpdateIsPending) {
561+
// The caller wanted a pending update
562+
// but there isn't currently one.
563+
resolve(nil);
564+
} else if (updateState == CodePushUpdateStateRunning && currentUpdateIsPending) {
565+
// The caller wants the running update, but the current
566+
// one is pending, so we need to grab the previous.
567+
resolve([CodePushPackage getPreviousPackage:nil]);
568+
} else {
569+
// The current package satisfies the request:
570+
// 1) Caller wanted a pending, and there is a pending update
571+
// 2) Caller wanted the running update, and there isn't a pending
572+
// 3) Calers wants the latest update, regardless if it's pending or not
573+
if (isRunningBinaryVersion) {
574+
// This only matters in Debug builds. Since we do not clear "outdated" updates,
575+
// we need to indicate to the JS side that somehow we have a current update on
576+
// disk that is not actually running.
577+
[package setObject:@(YES) forKey:@"_isDebugOnly"];
578+
}
579+
580+
resolve(package);
556581
}
557-
558-
// Add the "isPending" virtual property to the package at this point, so that
559-
// the script-side doesn't need to immediately call back into native to populate it.
560-
BOOL isPendingUpdate = [self isPendingUpdate:[package objectForKey:PackageHashKey]];
561-
[package setObject:@(isPendingUpdate) forKey:PackageIsPendingKey];
562-
563-
resolve(package);
564582
}
565583

566584
/*

ios/CodePush/CodePushPackage.m

Lines changed: 8 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@ @implementation CodePushPackage
1717
+ (void)clearUpdates
1818
{
1919
[[NSFileManager defaultManager] removeItemAtPath:[self getCodePushPath] error:nil];
20-
[[NSFileManager defaultManager] removeItemAtPath:[self getStatusFilePath] error:nil];
2120
}
2221

2322
+ (void)downloadAndReplaceCurrentBundle:(NSString *)remoteBundleUrl
@@ -290,27 +289,8 @@ + (NSString *)getCodePushPath
290289

291290
+ (NSDictionary *)getCurrentPackage:(NSError **)error
292291
{
293-
NSString *folderPath = [CodePushPackage getCurrentPackageFolderPath:error];
294-
if (!*error) {
295-
if (!folderPath) {
296-
return nil;
297-
}
298-
299-
NSString *packagePath = [folderPath stringByAppendingPathComponent:@"app.json"];
300-
NSString *content = [NSString stringWithContentsOfFile:packagePath
301-
encoding:NSUTF8StringEncoding
302-
error:error];
303-
if (!*error) {
304-
NSData *data = [content dataUsingEncoding:NSUTF8StringEncoding];
305-
NSDictionary* jsonDict = [NSJSONSerialization JSONObjectWithData:data
306-
options:kNilOptions
307-
error:error];
308-
309-
return jsonDict;
310-
}
311-
}
312-
313-
return nil;
292+
NSString *packageHash = [CodePushPackage getCurrentPackageHash:error];
293+
return [CodePushPackage getPackage:packageHash error:error];
314294
}
315295

316296
+ (NSString *)getCurrentPackageBundlePath:(NSError **)error
@@ -423,6 +403,12 @@ + (NSString *)getPackageFolderPath:(NSString *)packageHash
423403
return [[self getCodePushPath] stringByAppendingPathComponent:packageHash];
424404
}
425405

406+
+ (NSDictionary *)getPreviousPackage:(NSError **)error
407+
{
408+
NSString *packageHash = [CodePushPackage getPreviousPackageHash:error];
409+
return [CodePushPackage getPackage:packageHash error:error];
410+
}
411+
426412
+ (NSString *)getPreviousPackageHash:(NSError **)error
427413
{
428414
NSDictionary *info = [self getCurrentPackageInfo:error];
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
#import "CodePush.h"
2+
#import "RCTConvert.h"
3+
4+
// Extending the RCTConvert class allows the React Native
5+
// bridge to handle args of type "CodePushUpdateState"
6+
@implementation RCTConvert (CodePushUpdateState)
7+
8+
RCT_ENUM_CONVERTER(CodePushUpdateState, (@{ @"codePushUpdateStateRunning": @(CodePushUpdateStateRunning),
9+
@"codePushUpdateStatePending": @(CodePushUpdateStatePending),
10+
@"codePushUpdateStateLatest": @(CodePushUpdateStateLatest)
11+
}),
12+
CodePushUpdateStateRunning, // Default enum value
13+
integerValue)
14+
15+
@end

0 commit comments

Comments
 (0)