使用xcodebuild(Xcode 8)和CI(Travis / Jenkins)环境中的自动签名

时间:2016-09-14 22:32:07

标签: xcode jenkins continuous-integration travis-ci xcodebuild

随着Xcode 8的发布,Apple推出了一种管理签名配置的新方法。现在,您有两个选项ManualAutomatic

根据WWDC 2016年会议关于代码签名(WWDC 2016 - 401 - What's new in Xcode app signing),当您选择Automatic签名时,Xcode将会:

  • 创建签名证书
  • 创建和更新应用ID
  • 创建和更新配置文件

但根据Apple在该会话中所说的内容,Automatic Signing将使用Development signing,并且仅限于Xcode创建的配置文件。

当您尝试在CI环境(如Travis CI或Jenkins)上使用Automatic Signing时,会出现此问题。我无法找到一种简单的方法来继续使用自动和签名分发(因为Xcode强制您使用开发和Xcode创建的配置文件)。

新的" Xcode创建的配置文件"不要出现在开发人员门户中,虽然我可以在我的机器中找到...我应该将这些配置文件移到CI机器上,构建Development并导出Distribution吗?有没有办法使用Automatic Signing覆盖xcodebuild

8 个答案:

答案 0 :(得分:59)

我使用Jenkins CI和Xcode插件基本上遇到了同样的问题。 我最终使用xcodebuild进行构建和编码处理。

0。先决条件

为了成功完成以下步骤,您需要安装必要的配置文件和证书。这意味着您的代码签名应该已经正常工作。

1。构建.xcarchive

xcodebuild -project <path/to/project.xcproj> -scheme <scheme-name> -configuration <config-name> clean archive -archivePath <output-path> DEVELOPMENT_TEAM=<dev-team-id>
  • DEVELOPMENT_TEAM:您的10位数开发者团队ID(类似于A1B2C3D4E5)

2。导出到.ipa

xcodebuild -exportArchive -archivePath <path/to/your.xcarchive> -exportOptionsPlist <path/to/exportOptions.plist> -exportPath <output-path>

exportOptions.plist的示例:

<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>method</key>
    <string>development</string>
    <key>teamID</key>
    <string> A1B2C3D4E5 </string>
</dict>
</plist>
  • method:是developmentapp-storead-hocenterprise
  • 之一
  • teamID:您的10位数开发者团队ID(类似于A1B2C3D4E5)

与Jenkins Xcode插件相比,这个过程更接近你手动使用Xcode的过程。

注意:.xcarchive文件将始终处于开发状态,但在第二步中选择“app-store”作为方法将执行正确的分发签名,并将分发配置文件包含为“embedded.mobileprovision”。

希望这有帮助。

答案 1 :(得分:35)

尝试了几个选项后,这些是我能够在CI服务器上使用的解决方案:

  • 在CI环境中包含开发人员证书和私钥以及自动生成的配置文件:

使用Automatic signing强制您使用Developer证书和auto-generated provisioning profiles。一种选择是将开发证书和私钥(应用程序 - &gt;实用程序 - &gt; Keychain Access)和自动生成的配置文件导出到CI计算机。查找自动生成的配置文件的方法是导航到~/Library/MobileDevice/Provisioning\ Profiles/,将所有文件移动到备份文件夹,打开Xcode并存档项目。 Xcode将创建自动生成的开发配置文件,并将其复制到Provisioning Profiles文件夹。

xcodebuild archive ...将为.xcarchive创建一个Development签名。然后,xcodebuild -exportArchive ...可以重新设置Distribution

的构建版本
  • 替换&#39;自动&#39;用&#39;手册&#39;在CI环境中构建时

在致电xcodebuild之前,解决方法是在项目文件中将ProvisioningStyle = Automatic的所有实例替换为ProvisioningStyle = Manualsed可用于在pbxproj文件中简单查找替换:

sed -i '' 's/ProvisioningStyle = Automatic;/ProvisioningStyle = Manual;/' <ProjectName>.xcodeproj/project.pbxproj

@thelvis还使用xcodeproj gem创建了Ruby script来执行此操作。该脚本可让您更好地控制更改内容。

然后,

xcodebuild将使用项目中设置的代码签名标识(CODE_SIGN_IDENTITY)以及配置文件(PROVISIONING_PROFILE_SPECIFIER)。这些设置也可以作为参数提供给xcodebuild,它们将覆盖项目中设置的代码签名标识和/或配置文件。

  

编辑:使用Xcode 9,xcodebuild有一个新的构建设置参数CODE_SIGN_STYLE,可在AutomaticManual之间进行选择,因此无需查找和在项目文件中替换自动与手动的实例,WWDC 2017 Session 403 What's New in Signing for Xcode and Xcode Server

中的更多信息
  • 切换到手动签名

手动签名将完全控制正在使用的代码签名标识和配置文件。它可能是最干净的解决方案,但缺点是失去了自动签名的所有好处。

要了解有关使用Xcode 8进行代码签名的更多信息,我确实推荐此article以及WWDC2016会话401 - What's new in Xcode app signing

答案 2 :(得分:2)

我正在考虑另一种我尚未在此提及过的选项。设置两个相同的目标,只在其签名设置上有所不同。

  • 开发目标使用自动签名在添加新设备/开发人员时获得所有这些好处
  • CI目标使用人工签名

缺点是您必须管理两个相同的目标。好处是获得自动签名开发的好处,并且不必维护可能在构建时间之前修改项目的脆弱脚本。

答案 3 :(得分:2)

如果您使用Xcode 8.x和Jenkins进行CI。那么可能你会遇到问题&#34;签署“YourProjectName&#34;需要一个开发团队。在项目编辑器中选择一个开发团队。

产品类型&#39;应用程序&#39;需要进行代码签名。在SDK&#39; iOS 10.1'“。**在运行作业时建立失败**。

解决方案是什么?。

解决方案是:

  1. 在Xcode项目构建设置中将Provisioning profile设置为None。

  2. 在jenkins中,在Xcode设置之前创建一个执行shell并编写以下命令

    sed -i '' 's/ProvisioningStyle = Automatic;/ProvisioningStyle = Manual;/' ProjectName.xcodeproj/project.pbxproj 
    

    请记住:在jenkins的Build部分中的Xcode设置之前保持执行shell。

  3. 这很有效。

答案 4 :(得分:1)

对我来说,没有任何效果。我通过更改Mac Mini(带Jenkins的CI服务器)上安装的Xcode应用程序中的文件解决了我的问题,如以下链接所示:
https://www.jayway.com/2015/05/21/fixing-your-ios-build-scripts/
另外我关闭了Xcode的自动签名。

全部完成!终于有效!

答案 5 :(得分:0)

我注意到我的Unity构建从未向我的XCode项目添加ProvisioningStyle键。然后我找到了一种使用“PostProcessBuild”构建脚本手动添加ProvisioningStyle的方法。即在Unity构建IOS XCode项目之后调用的代码单元。

首先,我看一下project.pbxproj文件应该是什么样子 - 当它设置为Manual Provisioning时:

/* Begin PBXDictionary section */
    29B97313FDCFA39411CA2CEA /* Project object */ = {
        isa = PBXProject;
        attributes = {
            TargetAttributes = {
                1D6058900D05DD3D006BFB54 /* Unity-iPhone */ = {
                    ProvisioningStyle = Manual;
                };
                5623C57217FDCB0800090B9E /* Unity-iPhone Tests */ = {
                    TestTargetID = 1D6058900D05DD3D006BFB54 /* Unity-iPhone     */;
                };
            };
        };

然后我创建了我的代码来复制上面看到的文件的“结构”。 (使用此处的XCodeEditor项目:XCodeEditor

[PostProcessBuild]
public static void OnPostProcessBuild(BuildTarget target, string path)
{
    // Create a new project object from build target
    XCProject project = new XCProject(path);

    if (target == BuildTarget.iOS)
    {
        //Add Manual ProvisioningStyle - this is to force manual signing of the XCode project
        bool provisioningSuccess = AddProvisioningStyle(project, "Manual");

        if (provisioningSuccess)
            project.Save();
    }
}

private static bool AddProvisioningStyle(XCProject project, string style)
{
    var pbxProject = project.project;

    var attr = pbxProject.data["attributes"] as PBXDictionary;
    var targetAttributes = attr["TargetAttributes"] as PBXDictionary;

    var testTargetIDGuid = FindValue(targetAttributes, "TestTargetID");

    if (!string.IsNullOrEmpty(testTargetIDGuid))
    {
        var settings = new PBXDictionary();
        //here we set the ProvisioningStyle value
        settings.Add("ProvisioningStyle", style);

        targetAttributes.Add(testTargetIDGuid, settings);

        var masterTest = FindValue(targetAttributes, "ProvisioningStyle");

        if (masterTest == style)
        {
            return true;
        }
    }

    return false;
}

private static string FindValue(PBXDictionary targetAttributes, string key)
{
    foreach (var item in targetAttributes)
    {
        var ma = item.Value as PBXDictionary;

        foreach (var di in ma)
        {
            var lookKey = di.Key;

            if (lookKey == key)
            {
                return di.Value.ToString();
            }
        }
    }

    return "";
}

答案 6 :(得分:0)

为我解决的是:http://code-dojo.blogspot.jp/2012/09/fix-ios-code-signing-issue-when-using.html

...将证书从登录钥匙串复制到系统钥匙串。 您可能还希望将所有开发证书设置为“允许所有应用程序访问此项目”(右键单击/获取信息/访问控制)。

答案 7 :(得分:0)

有一个名为fastlane的工具,它使得使用xcodebuild变得更加容易并且维护它意味着新的更新将继续为xcode的更改提供支持。它使创建脚本和配置变得更加容易,可以在其支持的许多其他xcode自动化工具中构建和协调您的应用程序。我建议你仔细研究一下。