Saltare al contenuto principale

Costruzione IOS automatica con Capacitor azioni con certificato GitHub

Come configurare una pipeline di Integrazione Continua/Continua Integrazione per il tuo app IOS Ionic utilizzando fastlane e GitHub azioni in 5 minuti (2024)

Martin Donadieu

Martin Donadieu

Content Marketer

Costruzione IOS automatica con Capacitor azioni con certificato GitHub

Configurare l'Integrazione Continua/Continua Integrazione per gli app Capacitor può essere complesso e richiede molto tempo. Ecco cosa devi sapere:

Consigliamo ora di utilizzare Capgo Costruzione con il Capgo CLI per costruzione nativa Capacitor. Questa guida di Fastlane viene mantenuta per i team che mantengono pipeline di azioni GitHub esistenti, ma nuove costruzioni iOS dovrebbero utilizzare il Capgo CLI in modo da non dover mantenere Fastlane, esecutori Xcode, certificati e script di caricamento da soli.

Costruzione Capgo per CI/CD da Capgo

Svuota la manutenzione di Fastlane, esecutori Xcode, certificati, profili di provisioning e script di caricamento. Costruzione Capgo esegue costruzioni native firmate iOS direttamente dalla tua pipeline CI/CD esistente:

  • Funziona con la tua pipelineTrasmetti la costruzione Capgo da GitHub Actions, GitLab CI, Jenkins o script locali dopo la costruzione web e npx cap sync.
  • Firma da segreti CIMantieni le chiavi di App Store Connect, i certificati, i profili di provisioning, le password e gli ID di team nei tuoi segreti CI.
  • Nessuna manutenzione dell'esecutore nativoLa costruzione Capgo fornisce ambienti di costruzione Apple mantenuti, quindi non devi gestire gli esecutori macOS, le immagini Xcode o le vie di Fastlane.
  • Articoli e sottoscrizione: Scarica gli artefatti firmati per la QA o invia i build di rilascio attraverso il Capgo CLI.

Prenotazione

  • piani Capgo iniziano da 12€/mese
  • Incluse le aggiornamenti OTA e circa 15 build nativi al mese
  • I minuti aggiuntivi per i build sono fatturati per minuto attraverso i crediti

Configura Capgo Build in CI/CD

Guida di configurazione manuale

Ecco cosa devi fare:

L'invio continuo per iOS utilizzando Fastlane e GitHub Azioni e certificato

Prerequisiti

Prima di continuare con il tutorial:

  • Assicurati di avere Fastlane installato sulla tua macchina di sviluppo.
  • Assicurati di essere membro del programma di sviluppatore iOS.

Informazioni importanti sul prezzo

Prezzo GitHub Action

https://github.com/features/actions

Il servizio è ‘gratuito’ fino al limite, a seconda della macchina scelta.
Stiamo utilizzando un macOS Potete vedere nel screenshot il prezzo e i limiti (i prezzi sono validi alla data di creazione del tutorial e potrebbero subire modifiche in futuro)

Una volta informati sui requisiti e sui prezzi, continuiamo.

Nota: Nell'articolo si assume che tu abbia già creato l'app in App Store Connect. L'informazione importante verrà copiata da Fastlane!

Cosa imparerai in questo tutorial

Passaggi da seguire in questo post

  1. Utilizzare App Store Connect API con Fastlane
    • Requisiti:
      • Creazione di una chiave App Store Connect API
      • Utilizzo di una chiave App Store Connect API
  2. Copiare i file di Fastlane
  3. Configurare le azioni di GitHub

1. Utilizzare App Store Connect API con Fastlane

A partire da febbraio 2021, l'autenticazione a due fattori o la verifica a due passaggi è richiesta per tutti gli utenti per accedere a App Store Connect. Questo strato aggiuntivo di sicurezza per il tuo ID Apple aiuta a garantire che tu sia l'unica persona che può accedere al tuo account.
Da Supporto Apple

Requisiti

Per poter utilizzare App Store Connect API con Fastlane per caricare il tuo app, devi fornire i seguenti tre cose:

  1. ID emittente
  2. ID chiave
  3. File chiave o contenuto della chiave

Ottieni una chiave App Store Connect API

Per generare le chiavi, devi avere le autorizzazioni di amministratore in App Store Connect. Se non ne hai, puoi dirigere la persona interessata a questo articolo.

  1. Accedi a App Store Connect.

  2. Seleziona Utenti e accesso.

Accesso all'utente di App Store Connect

3 — Seleziona la scheda di integrazione.

Integrazione App Store Connect API

  1. Clicca su Genera chiave API o sul pulsante Aggiungi (+).

Le chiavi App Store Connect API creano

  1. Inserisci un nome per la chiave. Il nome è solo per la tua referenza e non fa parte della chiave stessa.

Le chiavi App Store Connect API creano nome

6 — Sotto Accesso, seleziona il ruolo per la chiave. I ruoli che si applicano alle chiavi sono gli stessi ruoli che si applicano agli utenti del tuo team. Vedi ruoli autorizzazioni. Raccomandiamo di selezionare Gestore App.

  1. Clicca su Generate.

L'accesso di una chiave API non può essere limitato a specifiche app.

Il nome della chiave, l'ID della chiave, un link di download e altre informazioni vengono visualizzati sulla pagina.

Chiavi di download per App Store Connect

Ecco dove puoi trovare tutte e tre le informazioni necessarie.
<1> ID della questione. (APPLE_ISSUER_ID segreto)
<2> ID della chiave. (APPLE_KEY_ID segreto)
<3> Clicca su "Scarica chiave API" per scaricare la tua chiave API privata. Il link di download compare solo se la chiave privata non è stata ancora scaricata. Apple non conserva una copia della chiave privata. Pertanto, puoi scaricarla solo una volta.

🔴 Conserva la tua chiave privata in un luogo sicuro. Non dovresti mai condividere le tue chiavi, archiviare le chiavi in un code repository o includere le chiavi nei code client-side.

Utilizzo di una chiave API di App Store Connect

Il file della chiave API (file p8 che hai scaricato), l'ID della chiave e l'ID dell'emittente sono necessari per creare il token JWT di autorizzazione. Ci sono diverse modalità in cui questa informazione può essere passata in Fastlane. Ho scelto di utilizzare l'azione nuova di Fastlane app_store_connect_api_key. Puoi imparare altre modalità in documentazione di Fastlane. Mostra questo metodo perché penso che sia la via più facile da utilizzare con la maggior parte dei CI, dove puoi impostare le variabili di ambiente.

Per favore converti il file p8 che hai scaricato in Base64 e memoralo come un segreto (APPLE_KEY_CONTENT).

base64 -i APPLE_KEY_CONTENT.p8 | pbcopy

Ora possiamo gestire App Store Connect con Fastlane utilizzando la chiave API, fantastico!

2. Certificati

Apri XCode e vai a Impostazioni > Account > ID Apple > Team e seleziona il tuo team.

Code identità di firma

Clicca su Gestisci certificati.

Se non hai già creato un certificato, puoi creare un nuovo certificato.

Clicca su + e selezionare Distribuzione Apple

Distribuzione Apple

Poi devi andare alla chiave di sistema per scaricare il certificato come .p12 file.

Per farlo, devi andare alla chiave di sistema, passare alla sezione login chiave di sistema e poi alla scheda I miei certificati.

I miei certificati

Poi puoi selezionare il certificato che desideri scaricare. (Cerca per la data del certificato)

E poi fai clic destro sul chiave privata del certificato e selezionare Esporta.

Scegli il formato del file Scambio informazioni personali (.p12).

Questo scaricherà il certificato come un .p12 file.

Per favore apri il file in un terminale e utilizza il seguente comando per convertirlo in Base64:

base64 -i BUILD_CERTIFICATE.p12 | pbcopy

Questo diventerà il tuo BUILD_CERTIFICATE_BASE64 segreto. Inoltre, quando richiesto, per favore fornisci la password del certificato. Questa password sarà il tuo P12_PASSWORD segreto.

3. Profili di provisioning

Apri Apple Developer e seleziona l'equipe giusta.

Poi crea un nuovo profilo, cliccando su +

Crea un nuovo profilo

E seleziona App Store Connect.

Seleziona App Store Connect

Poi devi selezionare l'app giusta, attenzione non puoi utilizzare wildcard altrimenti la firma fallirà.

Seleziona l'app giusta

Seleziona il certificato giusto che hai creato prima (cerca la data di scadenza dovrebbe essere lo stesso giorno e mese di oggi) e clicca su Continua.

Seleziona il certificato giusto

Infine inserisci il nome del profilo e clicca su Genera.

Il nome verrà utilizzato per identificare il profilo in Fastlane, sotto il valore di APPLE_PROFILE_NAME.

Genera il profilo

È possibile scaricare il profilo come un .mobileprovision file.

Scarica il profilo

Per favore converti il profilo in Base64 e memorizzalo come un segreto (BUILD_PROVISION_PROFILE_BASE64).

base64 -i BUILD_PROVISION_PROFILE.mobileprovision | pbcopy

4. Copia i file di Fastlane

Fastlane è una libreria Ruby creata per automatizzare le attività di sviluppo mobile comuni. Utilizzando Fastlane, puoi configurare delle

Create the Fastlane folder at the root of your Capacitor/Ionic project and add the Fastfile there:

  • personalizzate che raccolgono una serie di <project-root>/fastlane/
  • azioni <project-root>/fastlane/Fastfile

Questo è lo stesso livello di package.json, capacitor.config.*e il ios/ cartella. Non creare all'interno di ios/App/.

platform :ios do
  desc 'Export ipa and submit to TestFlight'
  lane :beta do
    keychain_info = { keychain_name: "ios-build-#{Time.now.to_i}.keychain", keychain_password: SecureRandom.uuid }
    
    begin
      setup_signing(keychain_info)
      bump_build_number
      build_app_with_signing(keychain_info)
      submit_to_testflight
    ensure
      cleanup_keychain(keychain_info)
    end
  end

  private_lane :setup_signing do |options|
    create_keychain(
      name: options[:keychain_name],
      password: options[:keychain_password],
      unlock: true,
      timeout: 0,
      lock_when_sleeps: false, 
      add_to_search_list: true
    )
    import_cert(options)
    install_profile
    update_project_settings
  end

  lane :bump_build_number do
		file = File.read('../package.json')
		data_hash = JSON.parse(file)
		api_key = app_store_connect_api_key(
      key_id: ENV['APPLE_KEY_ID'],
      issuer_id: ENV['APPLE_ISSUER_ID'],
      key_content: ENV['APPLE_KEY_CONTENT'],
      is_key_content_base64: true,
      duration: 1200,
      in_house: false
    )
		build_num = app_store_build_number(
      api_key: api_key,
			app_identifier: ENV['BUNDLE_IDENTIFIER'],
			live: false
    )
		build_num = build_num + 1
		UI.message("Bumped build number to #{build_num}")
		increment_build_number(
			build_number: build_num,
			xcodeproj: "./ios/App/App.xcodeproj",
			skip_info_plist: true
		)
	end

  private_lane :import_cert do |options|
    cert_path = "#{Dir.tmpdir}/build_certificate.p12"
    File.write(cert_path, Base64.decode64(ENV['BUILD_CERTIFICATE_BASE64']))
    import_certificate(
      certificate_path: cert_path,
      certificate_password: ENV['P12_PASSWORD'] || "",
      keychain_name: options[:keychain_name],
      keychain_password: options[:keychain_password],
      log_output: true
    )
    File.delete(cert_path)
  end  
  
  private_lane :cleanup_keychain do |options|
    delete_keychain(
      name: options[:keychain_name]
    )
  end  

  private_lane :install_profile do
    profile_path = "#{Dir.tmpdir}/build_pp.mobileprovision"
    File.write(profile_path, Base64.decode64(ENV['BUILD_PROVISION_PROFILE_BASE64']))
    UI.user_error!("Failed to create provisioning profile at #{profile_path}") unless File.exist?(profile_path)
    ENV['PROVISIONING_PROFILE_PATH'] = profile_path
    install_provisioning_profile(path: profile_path)
    File.delete(profile_path)
  end

  private_lane :update_project_settings do
    update_code_signing_settings(
      use_automatic_signing: false,
      path: "./ios/App/App.xcodeproj",
      code_sign_identity: "iPhone Distribution",
      profile_name: ENV['APPLE_PROFILE_NAME'],
      bundle_identifier: ENV['BUNDLE_IDENTIFIER'],
      team_id: ENV['APP_STORE_CONNECT_TEAM_ID']
    )
    update_project_team(
      path: "./ios/App/App.xcodeproj",
      teamid: ENV['APP_STORE_CONNECT_TEAM_ID']
    )
  end

  private_lane :build_app_with_signing do |options|
    unlock_keychain(
      path: options[:keychain_name],
      password: options[:keychain_password],
      set_default: false
    )
    build_app(
      workspace: "./ios/App/App.xcworkspace",
      scheme: "App",
      configuration: "Release",
      export_method: "app-store",
      output_name: "App.ipa",
      export_options: {
        provisioningProfiles: {
          ENV['BUNDLE_IDENTIFIER'] => ENV['APPLE_PROFILE_NAME']
        }
      },
      xcargs: "-verbose",
      buildlog_path: "./build_logs",
      export_xcargs: "-allowProvisioningUpdates",
    )
  end   

  private_lane :submit_to_testflight do
    api_key = app_store_connect_api_key(
      key_id: ENV['APPLE_KEY_ID'],
      issuer_id: ENV['APPLE_ISSUER_ID'],
      key_content: ENV['APPLE_KEY_CONTENT'],
      is_key_content_base64: true,
      duration: 1200,
      in_house: false
    )
    pilot(
      api_key: api_key,
      skip_waiting_for_build_processing: true,
      skip_submission: true,
      distribute_external: false,
      notify_external_testers: false,
      ipa: "./App.ipa"
    )
  end
end

5. Configurazione delle segrete

GitHub Azioni utilizza le segrete del repository che configuri nel passo successivo. Hai bisogno di un file locale solo se desideri eseguire o testare Fastlane dal tuo computer. .env Per il testing locale, crea

accanto al <project-root>/fastlane/.env Non commettere questo file. Aggiungi Fastfileal tuo fastlane/.env primo (o verificare che sia già ignorato). Ecco un esempio: .gitignore Ottieni l'ID del team di App Store Connect

APP_STORE_CONNECT_TEAM_ID=UVTJ336J2D
BUNDLE_IDENTIFIER=ee.forgr.testfastlane
# See previous section for these secrets
BUILD_CERTIFICATE_BASE64=
BUILD_PROVISION_PROFILE_BASE64=
APPLE_KEY_ID=
APPLE_ISSUER_ID=
APPLE_KEY_CONTENT=
P12_PASSWORD=
APPLE_PROFILE_NAME=

Getting the APP_STORE_CONNECT_TEAM_ID

Vai a Centro del Sviluppatore e scorri verso il basso fino a Membership details sezione. Il Team ID è il valore che devi impostare nella APP_STORE_CONNECT_TEAM_ID segreta.

app-store-connect-team-id

Ottenere il BUNDLE_IDENTIFIER

  1. Apri Xcode
  2. Doppio clic sul App nel navigatore dei progetti
  3. Poi clicca sulla scheda Signing and Capabilities
  4. Copia il valore di Bundle identifierQuesto è il valore che devi impostare nel BUNDLE_IDENTIFIER segreto.
bundle-identifier-xcode

6. Elaborazione Processing

In GitHub Azioni, sei fatturato in base ai minuti hai utilizzato per eseguire il flusso di lavoro CI/CD. Dalla mia esperienza, ci vogliono circa 10-15 minuti prima che un build possa essere elaborato in App Store Connect.

Per progetti privati, il costo stimato per build può arrivare a $0,08/min x 15 minuti = $1,2, o più, a seconda della configurazione e delle dipendenze del tuo progetto.

Se sei preoccupato per i costi per progetti privati, puoi impostare skip_waiting_for_build_processing a true. Questo salverà minuti di build non aspettando che App Store Connect completi il processo di build.

Tuttavia, ci sono un compromesso - dovrai aggiornare manualmente le informazioni sulla conformità dell'app in App Store Connect prima di poter distribuire il build agli utenti.

This optimization is mainly useful for private projects where build minutes cost money. For public/free projects, the build minutes are free so there’s no need to enable this setting. See GitHub’s Per i progetti pubblici/gratuiti, i minuti di build sono gratuiti quindi non c'è bisogno di abilitare questa impostazione. Vedi la pagina dei prezzi di __CAPGO_KEEP_0__ per maggiori dettagli.

7. Configura le azioni di GitHub

Configura i segreti di GitHub

Per favore copia i segreti dal .env file e incollali nel repository dei segreti di GitHub.

Vai a Impostazioni &gt; Segreti e variabili &gt; Azioni &gt; Nuovo segreto di repository

github-secrets

2. BUILD_CERTIFICATE_BASE64 - Certificato codificato in Base64.

3. BUILD_PROVISION_PROFILE_BASE64 - Profilo di provisioning codificato in Base64.

4. BUNDLE_IDENTIFIER - Identificatore del pacchetto dell'applicazione.

5. APPLE_KEY_ID — Chiave App Store Connect API 🔺ID della chiave.

6. APPLE_ISSUER_ID — ID della chiave emittente App Store Connect API 🔺.

7. APPLE_KEY_CONTENT — App Store Connect API Chiave 🔺 Contenuto della chiave .p8, controlla

8. Configura il file di workflow GitHub

Crea un directory di workflow GitHub.

cd .github/workflows

All'interno della workflow cartella, crea un file denominato build-upload-ios.ymle aggiungi il seguente contenuto.

name: Build source code on ios

on:
  push:
    tags:
      - '*'

jobs:
  build_ios:
    runs-on: macOS-latest
    steps:
      - uses: actions/checkout@v6
      - name: Set Node.js
        uses: actions/setup-node@v6
        with:
          node-version: 24
          cache: npm
      - name: Install dependencies
        id: install_code
        run: npm ci
      - name: Build
        id: build_code
        run: npm run build
      - uses: actions/cache@v5
        with:
          path: ios/App/Pods
          key: ${{ runner.os }}-pods-${{ hashFiles('**/Podfile.lock') }}
          restore-keys: |
            ${{ runner.os }}-pods-
      - name: Sync
        id: sync_code
        run: npx cap sync
      - uses: ruby/setup-ruby@v1
        with:
          ruby-version: '3.0'
          bundler-cache: true
      - uses: maierj/fastlane-action@v3.1.0
        env:
          APP_STORE_CONNECT_TEAM_ID: ${{ secrets.APP_STORE_CONNECT_TEAM_ID }}
          BUNDLE_IDENTIFIER: ${{ secrets.BUNDLE_IDENTIFIER }}
          BUILD_CERTIFICATE_BASE64: ${{ secrets.BUILD_CERTIFICATE_BASE64 }}
          BUILD_PROVISION_PROFILE_BASE64: ${{ secrets.BUILD_PROVISION_PROFILE_BASE64 }}
          APPLE_KEY_ID: ${{ secrets.APPLE_KEY_ID }}
          APPLE_ISSUER_ID: ${{ secrets.APPLE_ISSUER_ID }}
          APPLE_KEY_CONTENT: ${{ secrets.APPLE_KEY_CONTENT }}
          P12_PASSWORD: ${{ secrets.P12_PASSWORD }}
          APPLE_PROFILE_NAME: ${{ secrets.APPLE_PROFILE_NAME }}
        with:
          lane: ios beta
      - name: Upload release bundle
        uses: actions/upload-artifact@v6
        with:
          name: ios-release
          path: ./App.ipa
          retention-days: 10

Questo workflow dovrebbe essere attivato dopo ogni GitHub tag, se hai bisogno di automatizzare i tag, consulta Costruzione e rilascio automatico con GitHub azioni Primo.

Poi questo workflow estrarrà le dipendenze NodeJS, le installerà e costruirà il tuo'applicazione JavaScript.

Ogni volta che invii un nuovo commit, verrà costruito un rilascio in TestFlight.

La tua App non deve utilizzare Ionic, è sufficiente che abbia la base Capacitor obbligatoria, può avere un vecchio modulo Cordova, ma il plugin JS Capacitor dovrebbe essere preferito.

8. Attiva il workflow

Crea un Commit

Fai un commit, dovresti vedere il workflow attivo nel repository.

Attiva il workflow

Puoi inviare i nuovi commit sulla branch main o development per attivare il workflow.

Iniziato con il commit

Dopo pochi minuti, il build dovrebbe essere disponibile nel tuo dashboard App Store Connect.

Pannello di Testflight

9. Posso distribuire dalla macchina locale?

Sì, puoi farlo e non è affatto difficile.

Puoi utilizzare Xcode per costruire e firmare il tuo app, come sempre.

Guida alla configurazione CI/CD

Alternative piattaforme CI/CD

Aggiornamenti in tempo reale &amp; distribuzione

Grazie

Questo blog si basa sui seguenti articoli:

Continua a procedere dall'aggiornamento IOS automatico con Capacitor e GitHub azioni con certificato

Se stai utilizzando Aggiornamento IOS automatico con Capacitor e GitHub azioni con certificato per pianificare l'automazione CI/CD, connettilo con Capgo automazione CI/CD per il flusso di lavoro del prodotto in Capgo automazione CI/CD, Capgo Costruzioni native per il flusso di lavoro del prodotto in Capgo Costruzioni native, Capgo Integrazioni per il flusso di lavoro del prodotto in Capgo Integrazioni, Integrazione CI/CD per i dettagli di implementazione in Integrazione CI/CD, e GitHub Integrazione delle azioni per i dettagli di implementazione in GitHub Integrazione delle azioni.

Aggiornamenti in tempo reale per le app Capacitor

Quando un bug del layer web è attivo, invia la correzione attraverso Capgo invece di attendere giorni per l'approvazione della store. Gli utenti ricevono l'aggiornamento in background mentre le modifiche native rimangono nel normale percorso di revisione.

Inizia ora

Ultimi articoli dal nostro Blog

Capgo ti offre le migliori informazioni che ti servono per creare un'app mobile davvero professionale.