ARTICLE DETAIL

资讯详情

深耕商务建站与企业官网运营的一线实战洞察。

App Store Connect CLI 深度验证(--deep)设计解析:用缓存 Web 会话补齐提交前的 Web 专属阻塞项

App Store Connect CLI 深度验证(--deep)设计解析:用缓存 Web 会话补齐提交前的 Web 专属阻塞项 【免费下载链接】App-Store-Connect-CLIFast, scriptable CLI for the App Store Connect API. Automate TestFlight, builds, submissions, signing, analytics, screenshots, subscriptions, and more项目地址https://gitcode.com/gh_mirrors/ap/App-Store-Connect-CLI点击查看免费下载导读本文围绕 App Store Connect CLI 的asc validate --deep深度验证模式展开完整剖析其设计决策、五项 Web 专属发布闸门、私有端点契约、四态结果模型passed/blocked/unverified/notApplicable、解析度resolution输出与退出码约定并结合仓库源码internal/cli/validate/deep.go、internal/validation/deep.go说明底层实现原理。读完本文你将掌握如何在 CI 与本地发布管线中安全启用深度验证理解它为何只读、为何不启动交互式登录以及如何解读其 JSON 与表格输出。一、决策背景默认校验只覆盖公共 APIWeb 专属阻塞项留白asc validate是项目提供的权威 App Store 提交就绪性报告命令详见 commands/validate.mdx 与 internal/cli/validate/validate.go。默认模式下它只依赖公共 App Store Connect API可以覆盖以下内容元数据长度限制与必需字段、本地化完整性明显的模板残留文案Lorem ipsum、TODO、TBD、FIXME与关键词卫生告警App Store 审核信息App Review完整性、主分类配置Build 附加与处理状态、加密声明就绪性、内容权利声明定价计划与地区可用性、截图存在性与尺寸兼容性订阅审核就绪性与推广图指导、年龄分级完整性。然而有一类提交阻塞项只有通过已登录的 Apple 网页会话才能读取公共 API 无法给出确定性证据。设计文档 docs/design/validate-deep.md 的核心决策是在不改变默认行为的前提下为顶层就绪性命令增加一个显式、纯增量的深度模式--deep用已有的文件型缓存 Apple Web 会话把网页专属的不确定性替换为实时证据。决策要点如下默认asc validate保持纯公共 API 模式不引入会话依赖与私有接口脆弱性--deep先构建与默认模式完全相同的报告再基于已有缓存会话补充 Web 证据深度模式永不启动交互式登录、永不打开 Keychain没有可用缓存会话时报告仍然完整输出但会产生一条warning严重级别的深度验证未验证unverified发现并在已知 Apple Account 时给出精确的asc web auth login恢复命令--strict仍是显式的 fail-closed警告即阻塞策略。二、命令用法与标志契约深度验证的使用方式与普通校验一致只是追加--deepasc validate --app APP_ID --version 1.0.0 --deep asc validate --app APP_ID --version-id VERSION_ID --deep --apple-id userexample.com标志契约与 commands/validate.mdx 的 Flags 段落以及 internal/cli/validate/validate.go 的解析逻辑一致标志类型说明--appstring必填App Store Connect App ID也可通过ASC_APP_ID环境变量提供--versionstring版本字符串如1.2.0与--version-id互斥--version-idstringApp Store 版本 ID与--version互斥--platformstringIOS、MAC_OS、TV_OS、VISION_OS用于多平台歧义消解--strictboolean将警告含深度验证的 unverified 结果视为阻塞--check-urlsboolean对已填写的元数据 URL 目标做有界、隐私安全的公共 HTTP 检查--deepboolean校验需要缓存 Apple Web 会话才能验证的阻塞项并给所有可操作发现分类--apple-idstring为--deep选择某个用户自有的缓存 Web 会话不登录且仅在搭配--deep时有效--outputstringjson、table、markdown--prettyboolean美化打印 JSON几个容易被忽略的关键行为--apple-id只选择会话不触发登录。省略时使用最近一次缓存的 Web 会话与既有asc web子命令的行为一致。--apple-id离开--deep即用法错误。源码在 validate.go 中直接返回--apple-id requires --deep在认证与任何 HTTP 请求之前以退出码 2 写 stderr。顶层专属标志不被子命令静默忽略。--deep、--apple-id、--version、--version-id、--platform、--check-urls若被传给validate testflight、validate iap、validate subscriptions会被wrapValidateSubcommand包装逻辑拒绝见 validate.go杜绝标志看起来生效实则被忽略的隐患。深度验证只读不接受--confirm不会替你执行任何变更操作。默认版本选择当--version与--version-id都省略时命令会选择 App 最新且处于可编辑状态的版本PREPARE_FOR_SUBMISSION、DEVELOPER_REJECTED、REJECTED、METADATA_REJECTED、READY_FOR_REVIEW、WAITING_FOR_REVIEW、INVALID_BINARY其次回退到DEVELOPER_REMOVED_FROM_SALE版本最后回退到最新在售版本选择结果会打印到 stderr。默认选择只决定检查哪个版本被选中版本的状态仍按完整就绪性检查评估回退到在售版本并不代表它适合再次提交。三、深度验证的检查范围五项发布闸门设计文档明确 4.11 迭代只验证仓库中已具备只读客户端的 Web 专属提交阻塞项共五项App Privacy 发布状态privacy.publish_state待处理的 Apple Developer Program 协议与 App Store Connect 合同消息agreements.active首个自动续订订阅的附加状态subscriptions.first_type_app_version_attachment仅在尚无已批准订阅且至少一个订阅处于READY_TO_SUBMIT时相关初始可用性已配置availability.configured必需 App Review 字段完整review_information.required_fields前三项使用 Web 会话读取来源webSession后两项直接从既有公共检查派生来源publicApi因此不会触发重复请求也不会产生重复的根级发现。公共就绪性报告仍然对审核信息完整性、初始可用性、定价、元数据、截图、Build 状态、年龄分级、IAP 与订阅元数据保持权威——深度模式是丰富这些既有可操作发现而不是重复抓取。3.1 订阅附加检查的语义细节私有订阅字段描述的是附加到 App 的下一个版本而不是任意选中的版本。因此深度模式只在选中版本是当前审核候选时才评估该字段包括READY_FOR_REVIEW。规则如下终端历史版本如已上架版本→notApplicable公共 API 拿不到选中版本状态 →unverified已存在处于 App Store 审核中的订阅或已有订阅附加到下一版本审核 →passed已有一个自动续订订阅被批准 →notApplicableApple 的首个购买类型规则是 App 全局的首项被批准后后续订阅不再要求附加到应用版本存在READY_TO_SUBMIT订阅但都未附加且版本处于可编辑状态 →blocked且仅当候选唯一时才给出asc web review subscriptions attach --app ... --subscription-id ... --confirm变更命令多个候选时返回安全列表命令asc web review subscriptions list --app ...并把选择权留给操作者见 deep.go版本已离开可编辑状态如READY_FOR_REVIEW之后时即使检查仍进行也不会给出不安全的附加变更命令。可编辑版本状态集合PREPARE_FOR_SUBMISSION、DEVELOPER_REJECTED、REJECTED、METADATA_REJECTED、INVALID_BINARY与当前审核候选状态集合额外包含READY_FOR_REVIEW、WAITING_FOR_REVIEW、IN_REVIEW分别由isSubscriptionAttachmentEditableVersionState与isSubscriptionAttachmentVersionState实现deep.go。3.2 付费协议相关性的证据边界Paid Apps Agreement 的相关性不仅取决于活跃 IAP 与订阅还包括 App 当前的一次性下载价格。深度模式通过既有公共价格计划读取当前手动设置的应用价格report.HasPaidAppPrice。设计文档强调如果该证据不完整付费协议相关性报告为unverified绝不假设 App 是免费的也不凭空制造阻塞项。实现上对应requiresPaidAgreement : report.HasActiveMonetization || report.HasPaidAppPrice paidAgreementRelevanceKnown : requiresPaidAgreement || (report.MonetizationKnown report.AppPricingKnown)见 deep.go只有当MonetizationKnown与AppPricingKnown都为真且没有付费证据时才确定付费协议不相关否则相关性未知相关合同消息会被当作可疑证据处理。四、端点与响应契约零公共 OpenAPI 变更设计文档明确没有任何公共 App Store Connect OpenAPI 端点或请求模式变更。深度模式仅复用既有私有 Web 会话读取器GET /apps/{id}/dataUsagePublishState解码为AppDataUsagesPublishState { id, published }实现在 internal/web/privacy.goGetAppDataUsagesPublishStateGET /apps/{id}/subscriptionGroups附带订阅字段state、submitWithNextAppStoreVersion、isAppStoreReviewInProgress实现在 internal/web/subscription_review.goListReviewSubscriptions字段常量reviewSubscriptionsFields productId,name,state,isAppStoreReviewInProgress,submitWithNextAppStoreVersionGET /contractMessagesApp Store Connect 合同消息横幅加上 Developer Portal 的只读协议历史请求POST /services-account/QH65B2/account/getAgreementHistory合并解码为WebAgreementsStatusResult { pending, contractMessages, agreements }路径常量定义在 internal/web/agreements.go结构定义在 internal/asc/output_web_agreements.go。值得注意的是尽管协议历史使用 Apple 的POST 形状的私有只读端点深度验证绝不发送任何变更请求。App Privacy 发布与订阅附加的变更仍是独立命令且必须显式携带--confirm。订阅 Web 模型在 JSON 中增量暴露submitWithNextAppStoreVersionKnown位见 subscription_review.go 的ReviewSubscription结构。false的 presence 位意味着 Apple 省略了附加属性消费者不得把伴随的布尔值解读为确定未附加——这是实现中大量unverified分支存在的直接原因。五、输出与退出码契约5.1 输出形状JSON 仍是管道与 CI 的默认格式终端默认表格深度报告以增量方式附加为deep: { sessionStatus, summary, checks }既有字段的名称与含义保持不变结构定义见 internal/validation/types.goResolution 字段使用导出的 camelCase 结构体fixability、commands、appStoreConnectUrl表格与 Markdown 输出仅在深度模式提供解析数据时追加 resolution 列ApplyDeepValidationinternal/validation/deep.go将深度发现合并进公共报告并重建所有派生计数与有序修复计划。5.2 结果四态与来源每个深度检查都有确定性的单值结果status取值passed、blocked、unverified、notApplicablesource取值publicApi、webSession、manual类型常量见 types.go。会话本身的状态也被记录cached、expired、unavailable、validationFailed。成功的 Web 检查留在 deep 段中让调用方无需引入issue 形状的根级检查即可区分已验证与未检查。而以下情况是error 严重级别的根级发现App Privacy 状态未发布存在待处理协议缺少必需的首个同类订阅附加。无法验证的请求深度检查则是warning保留报告可用性同时把--strict作为显式 fail-closed 策略。5.3 解析度Resolution对象每个可操作的深度模式发现都会附带一个增量解析对象包含一个修复通道api-fixable、web-fixable或manual零个或多个精确的长格式asc命令一个稳定的 App Store Connect URL存在时。API 可修复的公共发现会携带已解析的资源 ID 与标志仅当缺失内容仍需操作者决策时才使用显式占位符。例如 internal/validation/deep.go 的publicAPIResolutionCommand会为版权缺失生成asc versions update --version-id VERSION_ID --copyright 2026 Your Company、为内容权利缺失生成asc apps update --id APP_ID --content-rights DECLARATION、为审核联系信息缺失生成asc review details-create --version-id ... --contact-first-name FIRST_NAME --contact-email EMAIL ...以及本地化字段对应的asc localizations update、asc review details-update等命令。Web 可修复发现则生成asc web privacy publish --app ... --confirm、asc web agreements accept --agreement-id ... --confirm、asc web review subscriptions attach ... --confirm。当--apple-id已知时scopeDeepResolutionCommandsdeep.go会把所有修复命令固定到该账户自动追加--apple-id ...且跳过已含该标志的命令保证后续变更不可能误用另一个缓存账户。5.4 退出码与错误路径完整报告总是先打印到 stdout然后命令按既有的validation reported-error退出契约返回存在阻塞项时非零退出见 validate.go用法错误如--apple-id不带--deep在认证或任何 HTTP 之前以退出码 2写 stderr独立 Web 检查失败不会抹掉成功的公共检查或其他深度结果而是变成带安全诊断文本的显式unverified发现原始响应体、Cookie、密码、提供方标识符与签名 URL永不进入报告选中的 Apple Account 邮箱只出现在账户作用域的修复命令中见 deep.go 的 session 警告 remediation。六、会话处理无交互、无 Keychain深度验证的会话加载路径loadDeepSessiondeep.go提供了--apple-id→webcore.ResumeCachedSessionWithoutPersist(ctx, appleID)未提供 →webcore.ResumeLastCachedSessionWithoutPersist(ctx)匹配asc web的默认行为两种情况都不会持久化、不会弹出交互式登录、不会触碰 Keychain。对应测试 internal/web/session_cache_test.go 中的TestResumeCachedSessionWithoutPersistNeverOpensKeychain与TestResumeCachedSessionWithoutPersistPreservesExpiredCache直接验证了这一约束。当会话缺失、过期或校验失败时buildDeepValidation会把三个 Web 检查全部标记为unverified并生成一个warning发现ID 为deep.web_session.unavailable/deep.web_session.expired/deep.web_session.validation_failedremediation 提示Inspect cached sessions with asc web auth status, or authenticate separately with asc web auth login --apple-id EMAIL and retry已知账户时该提示会升级为账户作用域版本并附加精确的asc web auth login --apple-id EMAIL命令deep.go。七、兼容性与生命周期设计文档把兼容性列为硬性约束源码实现与之严格一致变更完全增量保持所有既有默认调用、JSON 形状、退出行为与子命令不变--deep与--apple-id依赖 Apple 私有端点私有端点失败表示为unverified检查绝不静默当作成功顶层专属标志在validate testflight、validate iap、validate subscriptions前被拒绝任何子命令都不会悄悄忽略--deep或--apple-id深度验证保持只读不接受--confirmApp 创建、签名、构建/上传等零到审核的完整编排不在 4.11 范围内。八、验证与测试RED-GREEN 覆盖设计文档要求 RED 测试先于实现覆盖清单包括--deep与--apple-id的解析、顺序与顶层/子命令作用域--apple-id不带--deep时作为用法错误且 stdout 为空缓存会话缺失与过期行为且无交互式提示App Privacy 已发布/未发布两种状态协议活跃/待处理两种状态免费、一次性付费与不完整定价证据三种协议作用域情形无订阅、无就绪订阅、已附加的就绪订阅、就绪但未附加的首个同类订阅包括选中的READY_FOR_REVIEW版本不给出不安全附加变更一个私有端点失败时其余深度检查仍完成增量 JSON resolution 字段、API 可修复公共命令与条件性表格/Markdown 列稳定的阻塞计数、有序修复计划、stdout/stderr 与退出码。测试分布在 internal/cli/validate/deep_test.go、internal/cli/validate/validate_deep_help_test.go验证顶层专属标志、internal/cli/validate/diagnostics_test.go--apple-id requires --deep等文件中。聚焦包测试、命令级测试、生成的命令文档与构建产物共同覆盖变更面完整验证命令为make build make format make check-docs make lint ASC_BYPASS_KEYCHAIN1 make test现场冒烟测试是只读的仅在同时具备 API 凭据与缓存 Web 会话时运行任一缺失都会被如实报告而不是被隐藏。九、备选方案与后续工作设计文档记录了四个被否决的备选方案有助于理解为何采用--deep标志新建asc validate deep子命令会复制权威顶层校验器且标志放置更难被发现用户面对的是一个可选的验证深度决策用标志更清晰。让 Web 检查成为默认会给既有 CI 引入会话依赖与私有 API 脆弱性显式 opt-in 保住兼容性。asc launch或自动修复属于更大的编排与变更项目4.11 的深度验证刻意保持只读。通过 Web 端点重新实现审核信息与可用性会重复现有公共 API 证据丰富既有发现更小、更可信。明确推迟的工作包括自动化的--fix/--fix-web变更、验证内部的交互式登录与 2FA、App 创建/签名/构建上传等零到审核编排、没有经过验证的只读客户端支撑的 Web 检查以及把后续订阅当作仍需要应用版本的错误假设——一旦首个自动续订订阅获批该检查即变为notApplicable。十、落地建议把深度验证接入发布管线时请遵循以下边界先在本地用asc web auth login建立会话再运行asc validate --app ... --version-id ... --deep --apple-id EMAIL在 CI 中若无法保证缓存会话存在请使用--strict让unverified结果显式失败避免看起来通过的假阴性阅读 deep 段时区分sourcewebSession是实时证据publicApi是既有检查的派生结果unverified意味着证据缺失而非结论为假深度验证给出的修复命令都带--confirm且仅在你亲自执行时才会发生变更——它永远不会替你发布隐私、接受协议或附加订阅。延伸阅读设计文档docs/design/validate-deep.md命令文档commands/validate.mdx核心实现internal/cli/validate/deep.go、internal/cli/validate/validate.go领域模型internal/validation/types.go、internal/validation/deep.goWeb 读取器internal/web/privacy.go、internal/web/subscription_review.go、internal/web/agreements.go会话缓存语义internal/web/session_cache.go赞分享【免费下载链接】App-Store-Connect-CLIFast, scriptable CLI for the App Store Connect API. Automate TestFlight, builds, submissions, signing, analytics, screenshots, subscriptions, and more项目地址https://gitcode.com/gh_mirrors/ap/App-Store-Connect-CLI点击查看免费下载相关推荐App Store Connect CLI 的无状态 Web 会话--session-from-env 与 ASC_WEB_SESSION 设计解析App Store Connect CLI 的无状态 Web 会话 session from env 与 ASC_WEB_SESSION 设计解析 本篇技术指App-Store-Connect-CLI 全局只读模式深度指南用 ASC_READ_ONLY 与 --read-only 保证 Agent、CI 与审计会话永不写入App Store Connect CLI 全局只读模式深度指南用 ASC_READ_ONLY 与 read only 保证 Agent、CI 与审计会话永不App-Store-Connect-CLI 本地公证票据 stapling 与校验staple / validate 命令的安全设计解析App Store Connect CLI 本地公证票据 stapling 与校验staple / validate 命令的安全设计解析 导读 本文聚焦 Ap上一篇徽章可访问性指南Badges4-README.md-Profile ARIA属性应用下一篇OpenChamber SDK 扩展开发完全指南从 Manifest 声明到 iframe Host 桥接实战创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表
PREV
查看更多资讯
NEXT
返回资讯列表