如何在运行时告知iOS应用程序是否正在通过TestFlight Beta安装运行

com*_*ial 110 ios testflight

是否有可能在运行时检测到已通过TestFlight Beta(通过iTunes Connect提交)与App Store安装了应用程序?您可以提交单个应用包,并通过它们提供.是否有可以检测安装方式的API?或收据是否包含允许确定此信息的信息?

com*_*ial 110

对于通过TestFlight Beta安装的应用程序,收据文件的命名StoreKit\sandboxReceipt与通常相同StoreKit\receipt.使用[NSBundle appStoreReceiptURL]您可以在URL的末尾查找sandboxReceipt.

NSURL *receiptURL = [[NSBundle mainBundle] appStoreReceiptURL];
NSString *receiptURLString = [receiptURL path];
BOOL isRunningTestFlightBeta =  ([receiptURLString rangeOfString:@"sandboxReceipt"].location != NSNotFound);
Run Code Online (Sandbox Code Playgroud)

请注意,这sandboxReceipt也是在本地运行构建时以及在模拟器中运行构建时的接收文件的名称.

  • 压缩版:`[[[[NSBundle mainBundle] appStoreReceiptURL] lastPathComponent] isEqualToString:@"sandboxReceipt"]`(如果运行TestFlight分布式二进制文件,则为True)来自[Supertop/Haddad](http://blog.supertop.co/post/ 108759935377 /应用开发商,朋友试试,testflight) (13认同)
  • 如上所述,这适用于设备上的本地测试,但不适用于模拟器.我添加了像#if TARGET_IPHONE_SIMULATOR isRunningInTestMode = YES; #endif显然,这需要#import <TargetConditionals.h> (7认同)
  • 6 年后,2020 年将按预期工作。 (5认同)
  • 在安装具有Ad Hoc分发的构建时,似乎也返回YES. (3认同)
  • 此方法不能在扩展束中使用,因为仅对主机束存在接收. (2认同)
  • 当我在设备或模拟器上通过Xcode作为调试版本安装时,我的iOS 8测试结果为"StoreKit/sandboxReceipt".因此,这可能无法准确区分*testflight*构建与所有其他构建. (2认同)
  • 2021 年仍按预期工作(需要向 Bugsnag 提供标识符以区分 TestFlight 与开发和生产版本)。 (2认同)
  • 这似乎不适用于 Mac 应用程序。在 TestFlight 分布式版本中,收据被命名为“receipt”。 (2认同)

小智 60

根据组合的答案,我创建了以下SWIFT助手类.使用此类,您可以确定它是debug,testflight还是appstore构建.

enum AppConfiguration {
  case Debug
  case TestFlight
  case AppStore
}

struct Config {
  // This is private because the use of 'appConfiguration' is preferred.
  private static let isTestFlight = NSBundle.mainBundle().appStoreReceiptURL?.lastPathComponent == "sandboxReceipt"

  // This can be used to add debug statements.
  static var isDebug: Bool {
    #if DEBUG
      return true
    #else
      return false
    #endif
  }

  static var appConfiguration: AppConfiguration {
    if isDebug {
      return .Debug
    } else if isTestFlight {
      return .TestFlight
    } else {
      return .AppStore
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

我们在项目中使用这些方法为每个环境提供不同的跟踪ID连接字符串:

  func getURL(path: String) -> String {    
    switch (Config.appConfiguration) {
    case .Debug:
      return host + "://" + debugBaseUrl + path
    default:
      return host + "://" + baseUrl + path
    }
  }
Run Code Online (Sandbox Code Playgroud)

要么:

  static var trackingKey: String {
    switch (Config.appConfiguration) {
    case .Debug:
      return debugKey
    case .TestFlight:
      return testflightKey
    default:
      return appstoreKey
    }
  }
Run Code Online (Sandbox Code Playgroud)

更新05-02-2016: 使用像#if DEBUG这样的预处理器宏的先决条件是设置一些Swift编译器自定义标志.本答案中的更多信息:https://stackoverflow.com/a/24112024/639227

  • 感谢您的回答,我发现它非常有帮助!同样值得一提的是,使用“#if targetEnvironment(simulator)”可以确定是否在模拟器中运行。所以我有 Simulator/TestFlight/AppStore 选项(就我而言,这比“调试”更受欢迎):-) (3认同)
  • @Urkman 确保您正在设置`-D DEBUG` 标志。更多信息可以在这里找到(http://stackoverflow.com/questions/24003291/ifdef-replacement-in-swift-language)。 (2认同)

Ser*_*nko 27

现代Swift版本,它考虑了模拟器(基于已接受的答案):

private func isSimulatorOrTestFlight() -> Bool {
    guard let path = Bundle.main.appStoreReceiptURL?.path else {
        return false
    }
    return path.contains("CoreSimulator") || path.contains("sandboxReceipt")
}
Run Code Online (Sandbox Code Playgroud)

  • @Ethan 这个答案是在我发表评论后编辑的;方法名称曾经是“isTestFlight()” (3认同)
  • 哇!有用!惊人的!对于同一个构建(一个构建在一个方案中构建,一个配置),为 TestFlight 返回 TRUE,为 AppStore 返回 FALSE。完美的!谢谢你! (2认同)

wzb*_*zon 11

Bundle+isProduction在 Swift 5.2 上使用扩展:

import Foundation

extension Bundle {
    var isProduction: Bool {
        #if DEBUG
            return false
        #else
            guard let path = self.appStoreReceiptURL?.path else {
                return true
            }
            return !path.contains("sandboxReceipt")
        #endif
    }
}
Run Code Online (Sandbox Code Playgroud)

然后:

if Bundle.main.isProduction {
    // do something
}
Run Code Online (Sandbox Code Playgroud)


Mar*_*rný 5

更新资料

这不再起作用。使用其他方法。

原始答案

这也适用:

if NSBundle.mainBundle().pathForResource("embedded", ofType: "mobileprovision") != nil {
    // TestFlight
} else {
    // App Store (and Apple reviewers too)
}
Run Code Online (Sandbox Code Playgroud)

检测到是否从苹果的Testflight下载了iOS应用程序中找到