Ios7 与iTunes AppStore相比,从IOS AppStore安装的应用程序表现不同

Ios7 与iTunes AppStore相比,从IOS AppStore安装的应用程序表现不同,ios7,app-store,itunes,app-store-connect,Ios7,App Store,Itunes,App Store Connect,我们发布了一个基于订阅的应用程序,当用户下载它时,它将作为一个试用应用程序启动。当他们购买应用内订阅时,他们将获得完整的应用 我们面临的问题是,如果用户从手机上使用AppStore应用程序安装应用程序,他们会得到完整版本(每个用户)。我知道他们什么也没买。但如果他们从iTunes下载该应用程序,并使用sync将该应用程序通过电脑安装到手机上,该应用程序将作为试用版启动,购买订阅的选项就在那里 有人告诉我,这与itunes索引有关,新版本可以解决这个问题,但新版本今天获得批准,我们也遇到了同样的问

我们发布了一个基于订阅的应用程序,当用户下载它时,它将作为一个试用应用程序启动。当他们购买应用内订阅时,他们将获得完整的应用

我们面临的问题是,如果用户从手机上使用AppStore应用程序安装应用程序,他们会得到完整版本(每个用户)。我知道他们什么也没买。但如果他们从iTunes下载该应用程序,并使用sync将该应用程序通过电脑安装到手机上,该应用程序将作为试用版启动,购买订阅的选项就在那里

有人告诉我,这与itunes索引有关,新版本可以解决这个问题,但新版本今天获得批准,我们也遇到了同样的问题

任何帮助都将不胜感激

里科

编辑:我已经测试了使用xCode simulator发送给苹果的同一版本,xCode simulator是一款实际设备,通过临时开发和使用iTunes打开ipa,它们都能正常工作。不知道还会发生什么

在启动时调用此方法:

// check in App Subscription status
-(void)checkInAppSubscriptionStatus{
NSString *accountType = FMAccountTypeTrial;
// get receipt
NSDictionary *receipt = [[FmIAPHelper sharedInstance] getStoreReceipt:NO];
 // if receipt found
if([(NSNumber*)[receipt objectForKey:@"status"] integerValue] == 0){
    // get exp date from receipt.
    NSString *expDateStr = [[[receipt objectForKey:@"latest_receipt_info"] objectAtIndex:0] objectForKey:@"expires_date"];
    NSString *productIdentifier = [[[receipt objectForKey:@"latest_receipt_info"] objectAtIndex:0] objectForKey:@"product_id"];
    // set subscription type based on product identifier
    NSString *subscriptionType = ([productIdentifier isEqualToString:FMInAppMonthSubscription])? FMSubscriptionTypeMonthly : FMSubscriptionTypeYearly;
    expDateStr = [expDateStr stringByReplacingOccurrencesOfString:@"Etc/GMT" withString:@"GMT"];
    NSDateFormatter *df = [FM_UIViewController mysqlTimeStampFormatter];
    NSDate *expDate = [df dateFromString:expDateStr];
    // expiration date has passed.
    NSComparisonResult result = [expDate compare:[NSDate date]];
    if(result == NSOrderedDescending || result == NSOrderedSame){ // date still valid
        accountType = FMAccountTypePremium;
        // save data for latest receipt
        [[NSUserDefaults standardUserDefaults] setObject:subscriptionType forKey:FMSubscriptionTypeKey]; // monthly or yearly
        [[NSUserDefaults standardUserDefaults] setValue:receipt forKey:FMSubscriptionLastReceiptKey]; // last receipt
        [[NSUserDefaults standardUserDefaults] synchronize];
    }
    [[NSUserDefaults standardUserDefaults] setValue:expDate forKey:FMSubscriptionExpDateKey]; // expiration date
}
[[NSUserDefaults standardUserDefaults] setObject:accountType forKey:FMAccountTypeKey]; // premium or trial.
[[NSUserDefaults standardUserDefaults] synchronize]; //save
[self displayInitialContentView:@"InitialView"];
}

这是FMIAPHelper中的getStoreReceive方法

// get the latest receipt
// this returns an NSDictionary of the app's store receipt, status=0 for good, -1 for bad
- (NSDictionary *) getStoreReceipt:(BOOL)sandbox {
    NSArray *objects;
    NSArray *keys;
    NSDictionary *dictionary;
    BOOL gotreceipt = false;
@try {
    NSURL *receiptUrl = [[NSBundle mainBundle] appStoreReceiptURL];
    if ([[NSFileManager defaultManager] fileExistsAtPath:[receiptUrl path]]) {
        NSData *receiptData = [NSData dataWithContentsOfURL:receiptUrl];
        NSString *receiptString = [self base64forData:receiptData];
        if (receiptString != nil) {
            objects = [[NSArray alloc] initWithObjects:receiptString,FMiTunesConnectSharedSecret, nil];
            keys = [[NSArray alloc] initWithObjects:@"receipt-data",@"password", nil];
            dictionary = [[NSDictionary alloc] initWithObjects:objects forKeys:keys];
            NSError *error;
            NSData *data = [NSJSONSerialization dataWithJSONObject:dictionary options:NSJSONWritingPrettyPrinted error:&error];

            NSString *urlSting = @"https://buy.itunes.apple.com/verifyReceipt";
            if (sandbox) urlSting = @"https://sandbox.itunes.apple.com/verifyReceipt";
            NSString *postData = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
            dictionary = [self getJsonDictionaryWithPostFromUrlString:urlSting andDataString:postData];
            if ([dictionary objectForKey:@"status"] != nil) {
                if ([[dictionary objectForKey:@"status"] intValue] == 0) {
                    gotreceipt = true;
                }
            }
        }
    }

} @catch (NSException * e) {
    gotreceipt = false;
}

if (!gotreceipt) {
    objects = [[NSArray alloc] initWithObjects:@"-1", nil];
    keys = [[NSArray alloc] initWithObjects:@"status", nil];
    dictionary = [[NSDictionary alloc] initWithObjects:objects forKeys:keys];
}
return dictionary;
}
此方法处理试用信息的显示

// account type
FMAccountType = [[NSUserDefaults standardUserDefaults] objectForKey:FMAccountTypeKey];
if([[[NSUserDefaults standardUserDefaults] objectForKey:FMSubscriptionExemptKey] isEqualToString:FMSubscriptionExempt]) FMAccountType = FMAccountTypePremium;
if(FMAccountType == nil){
    FMAccountType = FMAccountTypeTrial;
}

代码的豁免部分在此版本中是新的,所以我知道这不是它。

这可能只是在您的设备上测试的问题吗?如果您让从未安装过此应用的朋友使用AppStore应用进行下载,会发生什么情况?同样的问题。它发生在测试设备(在配置文件中)和新设备上。我无法想象这两种安装方法会有什么不同,但如果您发布用于确定用户是否获得试用版或完整版的相关代码,可能会有所帮助。可能有人会注意到代码存在潜在问题。如果设备上有以前版本的应用程序,但后来被删除,并且用户试图在该设备上安装该应用程序(图标将是带有向下箭头的云,而不是“安装”按钮),则可能是该设备正在“重新启用”旧版本,手机上该设备的缓存版本。只是一个想法。