O caminho que envia um build para a App Store
Na Parte 1 criamos o target de build MAS e na Parte 2 criamos os arquivos de configuração e a ramificação de código que separam os dois canais. O target FocusTimer MAS agora está em uma forma que pode ser colocada na App Store.
Nesta parte final, vamos configurar o caminho para fazer o upload desse build para o App Store Connect e explicar como verificar os dois canais para que permaneçam íntegros daqui para frente, concluindo a série.
Como nas Partes 1 e 2,
FocusTimer,com.example.FocusTimer.mas, o Team IDABCDE12345e assim por diante são todos valores de exemplo.
Passo 1 — O ExportOptions-MAS.plist para upload
Na série de distribuição direta, observamos que ao exportar um archive para distribuição, o comando xcodebuild -exportArchive lê um ExportOptions.plist. O canal MAS precisa de um arquivo de configuração de exportação separado.
Crie um ExportOptions-MAS.plist no diretório de lançamento do projeto.
<?xml version="1.0" encoding="UTF-8"?>
<!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>app-store</string>
<key>destination</key>
<string>upload</string>
<key>signingStyle</key>
<string>automatic</string>
<key>teamID</key>
<string>ABCDE12345</string>
</dict>
</plist>
Aqui está o que cada chave significa.
method=app-store— Significa que este build é exportado para o canal da Mac App Store. Contrasta com odeveloper-iddo canal de distribuição direta.destination=upload— Faz com que oxcodebuild -exportArchivefaça o upload do artefato exportado diretamente para o App Store Connect. Não há necessidade de usar o Transporter ou uma ferramenta de upload separada como no passado.signingStyle=automatic— O Xcode combina automaticamente o perfil de provisionamento da Mac App Store e o certificado Apple Distribution.teamID— Seu Apple Developer Team ID.
Depois de criar este arquivo, reutilize-o para cada lançamento MAS. Deixe o ExportOptions.plist da distribuição direta como está e mantenha este arquivo ao lado dele.
Passo 2 — Registrar o registro de app no App Store Connect
Para realmente enviar o app para revisão, deve haver um registro (record) de app no App Store Connect. Um registro é o contêiner que armazena todas as informações exibidas na loja — o nome do app, descrição, capturas de tela, preço e assim por diante.
Criar o registro pode aguardar até pouco antes do seu primeiro envio real. Na etapa de configuração inicial, é suficiente saber com antecedência “quais itens decidir e como”. Em particular, o Primary Language abaixo é difícil de desfazer uma vez definido, então decida-o com cuidado antecipadamente.
Em App Store Connect → My Apps → + → New App, insira o seguinte.
- Platform — Selecione macOS
- Primary Language — ⚠️ O item a decidir com mais cuidado. Uma vez definido, é muito difícil alterá-lo por meio de autoatendimento. Se você planeja lançar o app em vários países, é comum definir English (U.S.) como idioma principal, porque o idioma principal é “o idioma de referência exibido quando não há tradução para um país específico”.
- App Name — O nome no idioma principal (ex.:
FocusTimer). Os nomes para outros idiomas são adicionados posteriormente separadamente como localizações por idioma. Por exemplo, você pode fazer com que os usuários coreanos vejam um nome em coreano e os usuários japoneses vejam um nome em japonês. - Bundle ID — Selecione
com.example.FocusTimer.masno menu suspenso. Esse é o ID que você registrou na Parte 1. Não confunda com o Bundle ID da distribuição direta (com.example.FocusTimer) — deve ser o que tem.masno final. - SKU — Uma string de identificação interna usada apenas por você. Não é exposta na loja, então você pode escolhê-la livremente (ex.:
focustimer-mas-001).
A categoria do app deve corresponder ao valor que você colocou em
LSApplicationCategoryTypenoInfo.plistna Parte 2. Se você colocoupublic.app-category.productivity(Produtividade) no plist, também deve escolher a categoria “Produtividade” no App Store Connect para que um aviso de incompatibilidade não apareça durante a revisão.
Passo 3 — Verificando os builds dos dois canais
Você agora tem uma única base de código com dois targets de build. Isso vem com um custo de manutenção. Se você normalmente só compila o canal de distribuição direta, não vai perceber se o target MAS quebrou silenciosamente. Por exemplo, você adiciona um novo código mas esquece a ramificação #if canImport(Sparkle), e só o build MAS falha na compilação.
A maneira mais confiável de evitar isso é fazer o archive do target MAS também toda vez que você fizer um lançamento de distribuição direta. Se o build for bem-sucedido, significa que a ramificação dos dois canais está íntegra.
xcodebuild -project FocusTimer.xcodeproj -scheme "FocusTimer MAS" \
-configuration Release \
-destination 'platform=macOS' \
-archivePath build/FocusTimer-MAS.xcarchive \
archive
Se você vir o seguinte ao final da saída, a ramificação do MAS está funcionando.
** ARCHIVE SUCCEEDED **
Recomendo incluir esse comando como último passo do seu script de automação de lançamento para que ele seja executado automaticamente em cada lançamento. Mesmo quando você não está realmente fazendo o upload do build MAS para a App Store, apenas confirmar que o archive é bem-sucedido é suficiente para garantir que a ramificação dos dois canais não quebrou.
Resumo da série — Configuração inicial para lançamento no MAS concluída
A configuração inicial de três partes para lançamento na Mac App Store está totalmente concluída. Você agora tem:
- ✅ (Parte 1) Um Bundle ID exclusivo para MAS + o target de build
FocusTimer MASduplicado - ✅ (Parte 2) Entitlements e Info.plist exclusivos para MAS + configurações de build + ramificação de código com
#if canImport(Sparkle) - ✅ (Parte 3) Um
ExportOptions-MAS.plistpara upload + como registrar um registro no App Store Connect + verificação dos builds dos dois canais
Com isso, um único app macOS agora tem os canais de distribuição direta (Developer ID) e Mac App Store. Para reafirmar a estrutura central:
- Compartilhe a mesma base de código, mas divida-a em dois targets de build.
- O target de distribuição direta inclui o Sparkle, e o target MAS o exclui.
- A diferença entre os dois é expressa por meio de arquivos de entitlements, Info.plist e ExportOptions separados e ramificação de código com
#if canImport(Sparkle).
A configuração inicial requer um bom esforço, mas também é uma estrutura que continua sendo reutilizada uma vez que está em vigor. A partir daí, quando você fizer um lançamento de distribuição direta, basta fazer o archive do build MAS junto e confirmar que a ramificação ainda está funcionando. O envio real para a App Store (capturas de tela, descrições, lidar com a revisão) é um trabalho separado feito sobre essa configuração inicial e é um tópico para outro artigo.