Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

Numele meu este Dmitri, lucrez ca tester în companie MEL Science. Recent am terminat de studiat o caracteristică destul de nouă de la Firebase Test Lab — anume, testarea instrumentală a aplicațiilor iOS folosind framework-ul nativ de testare XCUITest.

Înainte de asta, am încercat Firebase Test Lab pentru Android și mi-a plăcut foarte mult, așa că am decis să încerc să pun infrastructura de testare a proiectului iOS pe aceleași căi. A trebuit să caut multe informații pe Google și nu totul a mers din prima, așa că am decis să scriu un articol-tutorial pentru cei care se pregătesc să facă asta.

Așadar, dacă aveți teste UI pe un proiect iOS, puteți deja să încercați să le rulați pe dispozitive reale, oferite generos de Corporația Binelui. Cei interesați — bun venit sub titlu.

În narațiune, am decis să mă bazez pe unele date de bază — un repository privat pe GitHub și un sistem de construire CircleCI. Numele aplicației este AmazingApp, bundleID — com.company.amazingapp. Aceste date le ofer de la început pentru a reduce confuzia ulterioară.

Dacă ați implementat diferite soluții în proiectul vostru altfel — împărtășiți experiența în comentarii.

1. Testele în sine

Creăm o ramură nouă a proiectului pentru testele UI:

$ git checkout develop
$ git pull
$ git checkout -b “feature/add-ui-tests”

Voi deschide proiectul în XCode și voi crea un nou Target pentru testele UI [XCode -> File -> New -> Target -> iOS Testing Bundle], dându-i un nume sugestiv, AmazingAppUITests.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

Trecem în secțiunea Build Phases a Target-ului creat și verificăm existența Target Dependencies — AmazingApp, în Compile Sources — AmazingAppUITests.swift.

Este o bună practică să separați diverse variante de construire în Scheme-uri (Schemes) separate. Creăm un scheme pentru testele UI [XCode -> Product -> Scheme -> New Scheme] și îi dăm același nume: AmazingAppUITests.

Build-ul schemei create ar trebui să includă Target-ul aplicației principale — AmazingApp și Target-ul testelor UI — AmazingAppUITests — vezi captura de ecran.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

Apoi, creăm o nouă configurație de construire pentru testele UI. În XCode, dăm clic pe fișierul proiectului, trecem la secțiunea Info. Dăm clic pe “+” și creăm o nouă configurație, de exemplu XCtest. Aceasta ne va fi necesară ulterior, pentru a evita complicațiile atunci când va veni vorba de semnarea codului.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

În proiectul vostru există cel puțin trei Target-uri: aplicația principală, teste unitare (căci le aveți, nu-i așa?) și Target-ul UI testelor pe care l-am creat.

Accesăm Target AmazingApp, tab-ul Build Settings, secțiunea Code Signing Identity. Pentru configurația XCtest alegem iOS Developer. În secțiunea Code Signing Style alegem Manual. Profilul de provisioning nu l-am generat încă, dar ne vom întoarce la el mai târziu.

Pentru Target AmazingAppUITests facem același lucru, dar în câmpul Product Bundle Identifier introducem com.company.amazingappuitests.

2. Configurarea proiectului în Apple Developer Program

Accesăm pagina Apple Developer Program, mergem la secțiunea Certificates, Identifiers & Profiles și apoi la câmpul App IDs din Identifiers. Creăm un nou App ID cu numele AmazingAppUITests și bundleID com.company.amazingappuitests.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

Acum avem posibilitatea de a semna testele noastre cu un certificat separat, dar… Procedura de construire a build-ului pentru testare implică construirea aplicației în sine și construirea runner-ului de teste. Prin urmare, ne confruntăm cu problema semnării a două bundle ID cu un singur provisioning profile. Din fericire, există o soluție simplă și elegantă — Wildcard App ID. Repetăm procedura de creare a unui nou App ID, dar în loc de Explicit App ID alegem Wildcard App ID, așa cum se vede în captura de ecran.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

În această etapă, lucrul cu developer.apple.com s-a încheiat, dar nu vom închide fereastra browser-ului. Mergem la site-ul cu documentația pentru Fastlane și citim despre utilitarul Match de la început până la sfârșit.

Cititorul atent a observat că pentru a utiliza acest utilitar, ne va trebui un repository privat și un cont care are acces atât la Apple Developer Program, cât și la Github. Creăm (dacă nu există deja) un cont de tipul InfrastructureAccount@your.company.domain, alegem o parolă puternică, îl înregistrăm în developer.apple.com, numim administrator proiectului. Apoi, oferim contului acces la repository-ul github al companiei tale și creăm un nou repository privat cu numele ceva de genul AmazingAppMatch.

3. Configurarea Fastlane și utilitarului match

Deschidem terminalul, mergem în folderul proiectului și inițializăm fastlane așa cum este indicat în manualul oficial.După introducerea comenzii

$ fastlane init

ne va fi propus să alegem configurațiile disponibile pentru utilizare. Alegeți a patra opțiune — configurarea manuală a proiectului.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

În proiect a apărut un nou director fastlane, în care se află două fișiere - Appfile și Fastfile. Pe scurt - în Appfile stocăm datele de serviciu, iar în Fastfile definim job-urile, numite în terminologia Fastlane lanes. Recomand citirea documentației oficiale: unu, doi.

Deschidem Appfile în editorul nostru de text preferat și îl aducem la următoarea formă:

app_identifier "com.company.amazingapp"       # ID pachetului
apple_dev_portal_id "infrastructureaccount@your.company.domain"  # Contul de infrastructură creat care are dreptul de a edita proiectul iOS în Apple Developer Program.
team_id "LSDY3IFJAY9" # ID-ul echipei din Developer Portal

Ne întoarcem în terminal și conform manualului oficial, începem să configurăm match.

$ fastlane match init
$ fastlane match development

Apoi, introducem datele solicitate — depozitul, contul, parola etc.

Important: la prima rulare, utilitarul match va solicita introducerea parolei pentru decriptarea depozitului. Este foarte important să păstrăm această parolă, ne va fi utilă în etapa de configurare a serverului CI!

În folderul fastlane a apărut un nou fișier — Matchfile. Îl deschidem în editorul nostru de text preferat și îl aducem în forma:

git_url("https://github.com/YourCompany/AmazingAppMatch") #Repository privat creat pentru stocarea certificatelor și profilurilor.
type("development") # Tipul implicit poate fi: appstore, adhoc, enterprise sau development
app_identifier("com.company.amazingapp")
username("infrastructureaccount@your.company.domain") # Numele de utilizator Apple Developer Portal pentru contul infrastructural

Umplem exact în acest mod, dacă dorim să utilizăm ulterior match pentru semnarea build-urilor pentru publicare în Crashlytics și/sau AppStore, adică pentru semnarea ID-ului pachetului aplicației tale.

Dar, așa cum ne amintim, pentru semnarea build-ului de test am creat un ID Wildcard special. Așa că deschidem Fastfile și adăugăm un nou lane:

lane :testing_build_for_firebase do

    match(
      type: "development",
      readonly: true,
      app_identifier: "com.company.*",
      git_branch: "uitests"  # creăm un branș separat pentru certificatul de development pentru semnarea build-ului de test.
    )

end

Salvăm, introducem în terminal

fastlane testing_build_for_firebase

și vedem cum fastlane a creat un nou certificat și l-a plasat în depozit. Perfect!

Deschidem XCode. Acum avem profilul de provisioning necesar de tip Match Development com.company.*, care trebuie specificat în secțiunea Profil de provisioning pentru țintele AmazingApp și AmazingAppUITests.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

Rămâne să completăm lane-ul pentru compilarea testelor. Ne ducem la repository proiectul pluginului pentru fastlane, care simplifică configurarea exportului în Firebase Test Lab și urmăm instrucțiunile.

Copiem din exemplul inițial, astfel încât lane-ul nostru testing_build_for_firebase să arate așa:


 lane :testing_build_for_firebase do

    match(
      type: "development",
      readonly: true,
      app_identifier: "com.company.*",
      git_branch: "uitests"
    )

    scan(
      scheme: 'AmazingAppUITests',      # Schema de test UI
      clean: true,                        # Recomandat: Acesta va asigura că build-ul nu va include fișiere inutile
      skip_detect_devices: true,          # Necesar
      build_for_testing: true,            # Necesar
      sdk: 'iphoneos',                    # Necesar
      should_zip_build_products: true,     # Trebuie să fie adevărat pentru a seta formatul corect pentru Firebase Test Lab
    )

    firebase_test_lab_ios_xctest(
      gcp_project: 'AmazingAppUITests', # Numele proiectului tău Google Cloud
      devices: [                          # Dispozitiv(e) pe care se vor rula testele
        {
          ios_model_id: 'iphonex',        # ID model dispozitiv, vezi comanda gcloud de mai sus
          ios_version_id: '12.0',         # ID versiune iOS, vezi comanda gcloud de mai sus
          locale: 'en_US',                # Opțional: implicit la en_US dacă nu este setat
          orientation: 'portrait'         # Opțional: implicit la portret dacă nu este setat
        }
      ]
    )

  end

Pentru informații complete despre configurarea fastlane în CircleCI, recomand citirea documentației oficiale o dată, doi.

Nu uitați să adăugați noua sarcină în config.yml:

build-for-firebase-test-lab:
   macos:
     xcode: "10.1.0"
   working_directory: ~\/project
   shell: \/bin\/bash --login -o pipefail
   steps:
     - checkout
     - attach_workspace:
         at: ~\/project
     - run: sudo bundle install     # actualizăm dependențele
     - run:
         name: install gcloud-sdk   # pe mașina Mac trebuie să instalăm gcloud
         command: |
           ruby -e "$(curl -fsSL https:\/\/raw.githubusercontent.com\/Homebrew\/install\/master\/install)"  \/dev\/null ; brew install caskroom\/cask\/brew-cask 2> \/dev\/null
           brew cask install google-cloud-sdk
     - run:
         name: build app for testing
         command: fastlane testing_build_for_firebase  # pornim lane-ul de construire și trimitere în firebase

4. Și cum rămâne cu mediul nostru de testare? Configurăm Firebase.

Să începem, de fapt, cu scopul pentru care această articol a fost scris.

Poate că aplicația ta folosește Firebase pe un plan gratuit, poate că nu folosește deloc. Nu există o diferență semnificativă, deoarece pentru nevoile de testare putem crea un proiect separat cu un an de utilizare gratuită (cool, nu-i așa?)

Ne conectăm la contul nostru de infrastructură (sau orice alt cont, nu contează) și mergem la pagina consolei Firebase. Creăm un nou proiect numit AmazingAppUITests.

Important: În pasul anterior, în Fastfile în lane-ul firebase_test_lab_ios_xctest, parametrul gcp_project trebuie să corespundă numelui proiectului.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

Setările implicite ne mulțumesc pe deplin.

Nu închideți tab-ul, cu același cont ne înregistrăm în Gcloud — aceasta este o măsură necesară, deoarece comunicarea cu Firebase se face prin intermediul interfeței consolei gcloud.

Google oferă 300$ pe an, ceea ce, în contextul realizării testelor automate, echivalează cu un an de utilizare gratuită a serviciului. Introducem datele de plată, așteptăm debitarea de test de 1$ și primim 300$ în cont. După un an, proiectul va fi transferat automat pe un plan tarifar gratuit, așa că nu trebuie să ne facem griji cu privire la o eventuală pierdere de bani.

Să ne întoarcem la tab-ul proiectului Firebase și să-l mutăm pe planul tarifar Blaze — acum avem cu ce plăti în cazul depășirii limitei.

În interfața gcloud, selectăm proiectul nostru Firebase, alegem opțiunea din meniul principal „Catalog” și adăugăm Cloud Testing API și Cloud Tools Result API.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

Apoi, mergem la meniul „IAM și administrare” -> Conturi de serviciu -> Creare cont de serviciu. Acordăm drepturi de editare asupra proiectului.

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

Creăm o cheie API în format JSON

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS

JSON-ul descărcat ne va fi util puțin mai târziu, iar acum considerăm că configurarea Test Lab este completă.

5. Configurarea CircleCI

Se naște o întrebare rezonabilă — ce facem cu parolele? Pentru a ne stoca în siguranță parolele și alte date sensibile, ne ajută mecanismul variabilelor de mediu al mașinii noastre de build. În setările proiectului CircleCI, alegem Variabile de mediu

Lansăm teste instrumentale în Firebase Test Lab. Partea a 1-a: proiect iOS
Și adăugăm următoarele variabile:

  • key: GOOGLE_APPLICATION_CREDENTIALS
    value: conținutul fișierului json al cheii contului de serviciu gcloud
  • key: MATCH_PASSWORD
    value: parola pentru decriptarea repository-ului github cu certificatele
  • key: FASTLANE_PASSWORD
    value: parola contului infrastructural Apple Developer Portal

Salvăm modificările, creăm un PR și îl trimitem pentru recenzie șefului echipei.

Concluzii

Ca rezultat al acestei manevre simple, am obținut un stand bun, stabil, cu capacitatea de a înregistra videoclipuri pe ecranul dispozitivului în timpul testării. În exemplul de testare, am specificat modelul dispozitivului iPhone X, dar ferma oferă o gamă bogată de combinații de modele și versiuni iOS.

Partea a doua va fi dedicată configurării pas cu pas a Firebase Test Lab pentru un proiect Android.

Sursa: habr.com

Cumpără un hosting fiabil pentru site-uri cu protecție DDoS, servere VPS VDS 🔥 Cumpără un hosting fiabil pentru site-uri cu protecție DDoS, servere VPS VDS | ProHoster