Android-apps bouwen, testen en implementeren

Azure DevOps Services

U kunt pijplijnen instellen voor het automatisch bouwen, testen en implementeren van Android-toepassingen.

Vereisten

U moet de volgende items hebben:

  • GitHub-account. Als u geen GitHub-account hebt, maakt u er nu een.
  • Azure DevOps-project. Als u geen project hebt, maakt u er nu een.

Pijplijn instellen

Ga als volgt te werk om een pijplijn in te stellen voor een Android-voorbeeldtoepassing.

  1. Fork de volgende opslagplaats naar uw GitHub-account om de code voor een eenvoudige Android-toepassing op te halen.

    https://github.com/MicrosoftDocs/pipelines-android
    
  2. Meld u aan bij uw Azure DevOps-organisatie en ga naar uw project.

  3. Selecteer Pijplijnen>pijplijn maken of nieuwe pijplijn.

  4. Selecteer GitHub als de locatie van uw broncode.

    Screenshot showing list of repositories to select from.

    U wordt mogelijk omgeleid naar GitHub om u aan te melden. Voer in dat geval uw GitHub-referenties in.

  5. Selecteer de -android-opslagplaats die u eerder hebt gesplitst.

  6. Selecteer Goedkeuren en installeren op het scherm dat volgt.

    Azure Pipelines genereert een YAML-bestand voor uw pijplijn.

  7. Selecteer Uitvoeren.

  8. Voer rechtstreeks door naar de hoofdbranch en kies Opnieuw uitvoeren .

  9. Wacht totdat de uitvoering is voltooid.

U hebt een werkend YAML-bestand (azure-pipelines.yml) in uw opslagplaats dat u kunt aanpassen.

Tip

Als u wijzigingen wilt aanbrengen in het YAML-bestand, selecteert u de pijplijn op de pagina Pijplijnen en bewerkt u het azure-pipelines.yml bestand.

Bouwen met Gradle

Gradle is een veelgebruikt buildhulpprogramma dat wordt gebruikt voor het bouwen van Android-projecten. Zie de Gradle-taak voor meer informatie over uw opties.

# https://learn.microsoft.com/azure/devops/pipelines/ecosystems/android
pool:
  vmImage: 'macOS-latest'

steps:
- task: Gradle@2
  inputs:
    workingDirectory: ''
    gradleWrapperFile: 'gradlew'
    gradleOptions: '-Xmx3072m'
    publishJUnitResults: false
    testResultsFiles: '**/TEST-*.xml'
    tasks: 'assembleDebug'

Het buildpad aanpassen

  • Pas de waarde van de workingDirectory aan als uw gradlew bestand zich niet in de hoofdmap van de opslagplaats bevindt. De mapwaarde moet vergelijkbaar zijn met de hoofdmap van de opslagplaats, zoals AndroidApps/MyApp of $(system.defaultWorkingDirectory)/AndroidApps/MyApp.

  • Pas de waarde gradleWrapperFile aan als uw gradlew bestand zich niet in de hoofdmap van de opslagplaats bevindt. De waarde van het bestandspad moet vergelijkbaar zijn met de hoofdmap van de opslagplaats, zoals AndroidApps/MyApp/gradlew of $(system.defaultWorkingDirectory)/AndroidApps/MyApp/gradlew.

Gradle-taken aanpassen

Pas de taakwaarde aan voor de buildvariant die u wilt gebruiken, zoals assembleDebug of assembleRelease. Zie de volgende Google Android-ontwikkeldocumentatie voor meer informatie:

Een Android-pakket ondertekenen en uitlijnen (APK)

Als uw build de APK nog niet ondertekent en zipalignt , voegt u de Android-ondertekeningstaak toe aan de YAML. Een APK moet zijn ondertekend om te worden uitgevoerd op een apparaat in plaats van een emulator. Zipaligning vermindert het RAM-geheugen dat door de toepassing wordt gebruikt.

Belangrijk

U wordt aangeraden elk van de volgende wachtwoorden op te slaan in een geheime variabele.

- task: AndroidSigning@2
  inputs:
    apkFiles: '**/*.apk'
    jarsign: true
    jarsignerKeystoreFile: 'pathToYourKeystoreFile'
    jarsignerKeystorePassword: '$(jarsignerKeystorePassword)'
    jarsignerKeystoreAlias: 'yourKeystoreAlias'
    jarsignerKeyPassword: '$(jarsignerKeyPassword)'
    zipalign: true

Testen

Testen op de Android Emulator

Maak de Bash-taak en kopieer de onderstaande code om de emulator te installeren en uit te voeren. Vergeet niet om de emulatorparameters in te passen aan uw testomgeving. De emulator wordt gestart als achtergrondproces en is beschikbaar in latere taken.

#!/usr/bin/env bash

# Install AVD files
echo "y" | $ANDROID_HOME/cmdline-tools/latest/bin/sdkmanager --install 'system-images;android-27;google_apis;x86'

# Create emulator
echo "no" | $ANDROID_HOME/tools/bin/avdmanager create avd -n xamarin_android_emulator -k 'system-images;android-27;google_apis;x86' --force

$ANDROID_HOME/emulator/emulator -list-avds

echo "Starting emulator"

# Start emulator in background
nohup $ANDROID_HOME/emulator/emulator -avd xamarin_android_emulator -no-snapshot > /dev/null 2>&1 &
$ANDROID_HOME/platform-tools/adb wait-for-device shell 'while [[ -z $(getprop sys.boot_completed | tr -d '\r') ]]; do sleep 1; done; input keyevent 82'

$ANDROID_HOME/platform-tools/adb devices

echo "Emulator started"

Testen op door Azure gehoste apparaten

Voeg de App Center-testtaak toe om de toepassing te testen in een gehost lab met iOS- en Android-apparaten. Er is een gratis proefversie van App Center vereist, die later moet worden geconverteerd naar betaald.

Meld u eerst aan bij App Center .

# App Center test v1
# Test app packages with Visual Studio App Center.
- task: AppCenterTest@1
  inputs:
    appFile: # string. Alias: app. Required. Binary application file path. 
    artifactsDirectory: '$(Build.ArtifactStagingDirectory)/AppCenterTest' # string. Alias: artifactsDir. Required. Artifacts directory. Default: $(Build.ArtifactStagingDirectory)/AppCenterTest.
  # Prepare Tests
    #prepareTests: true # boolean. Alias: enablePrepare. Prepare tests. Default: true.
    frameworkOption: 'appium' # 'appium' | 'espresso' | 'calabash' | 'uitest' | 'xcuitest'. Alias: framework. Required when enablePrepare = true. Test framework. Default: appium.
    #appiumBuildDirectory: # string. Alias: appiumBuildDir. Required when enablePrepare = true && framework = appium. Build directory. 
    #espressoBuildDirectory: # string. Alias: espressoBuildDir. Optional. Use when enablePrepare = true && framework = espresso. Build directory. 
    #espressoTestApkFile: # string. Alias: espressoTestApkPath. Optional. Use when enablePrepare = true && framework = espresso. Test APK path. 
    #calabashProjectDirectory: # string. Alias: calabashProjectDir. Required when enablePrepare = true && framework = calabash. Project directory. 
    #calabashConfigFile: # string. Optional. Use when enablePrepare = true && framework = calabash. Cucumber config file. 
    #calabashProfile: # string. Optional. Use when enablePrepare = true && framework = calabash. Profile to run. 
    #calabashSkipConfigCheck: false # boolean. Optional. Use when enablePrepare = true && framework = calabash. Skip Configuration Check. Default: false.
    #uiTestBuildDirectory: # string. Alias: uitestBuildDir. Required when enablePrepare = true && framework = uitest. Build directory. 
    #uitestStorePath: # string. Optional. Use when enablePrepare = true && framework = uitest. Store file. 
    #uiTestStorePassword: # string. Alias: uitestStorePass. Optional. Use when enablePrepare = true && framework = uitest. Store password. 
    #uitestKeyAlias: # string. Optional. Use when enablePrepare = true && framework = uitest. Key alias. 
    #uiTestKeyPassword: # string. Alias: uitestKeyPass. Optional. Use when enablePrepare = true && framework = uitest. Key password. 
    #uiTestToolsDirectory: # string. Alias: uitestToolsDir. Optional. Use when enablePrepare = true && framework = uitest. Test tools directory. 
    #signInfo: # string. Optional. Use when framework = calabash || framework = uitest. Signing information. 
    #xcUITestBuildDirectory: # string. Alias: xcuitestBuildDir. Optional. Use when enablePrepare = true && framework = xcuitest. Build directory. 
    #xcUITestIpaFile: # string. Alias: xcuitestTestIpaPath. Optional. Use when enablePrepare = true && framework = xcuitest. Test IPA path. 
    #prepareOptions: # string. Alias: prepareOpts. Optional. Use when enablePrepare = true. Additional options. 
  # Run Tests
    #runTests: true # boolean. Alias: enableRun. Run tests. Default: true.
    credentialsOption: 'serviceEndpoint' # 'serviceEndpoint' | 'inputs'. Alias: credsType. Required when enableRun = true. Authentication method. Default: serviceEndpoint.
    #serverEndpoint: # string. Required when enableRun = true && credsType = serviceEndpoint. App Center service connection. 
    #username: # string. Required when enableRun = true && credsType = inputs. App Center username. 
    #password: # string. Required when enableRun = true && credsType = inputs. App Center password. 
    appSlug: # string. Required when enableRun = true. App slug. 
    devices: # string. Required when enableRun = true. Devices. 
    #series: 'master' # string. Optional. Use when enableRun = true. Test series. Default: master.
    #dsymDirectory: # string. Alias: dsymDir. Optional. Use when enableRun = true. dSYM directory. 
    localeOption: 'en_US' # 'da_DK' | 'nl_NL' | 'en_GB' | 'en_US' | 'fr_FR' | 'de_DE' | 'ja_JP' | 'ru_RU' | 'es_MX' | 'es_ES' | 'user'. Alias: locale. Required when enableRun = true. System language. Default: en_US.
    #userDefinedLocale: # string. Optional. Use when enableRun = true && locale = user. Other locale. 
    #loginOptions: # string. Alias: loginOpts. Optional. Use when enableRun = true && credsType = inputs. Additional options for login. 
    #runOptions: # string. Alias: runOpts. Optional. Use when enableRun = true. Additional options for run. 
    #skipWaitingForResults: false # boolean. Alias: async. Optional. Use when enableRun = true. Do not wait for test result. Default: false.
  # Advanced
    #cliFile: # string. Alias: cliLocationOverride. App Center CLI location. 
    #showDebugOutput: false # boolean. Alias: debug. Enable debug output. Default: false.

Artefacten behouden met de buildrecord

Voeg de taken Voor het kopiëren van bestanden toe en publiceer buildartefacten . Uw APK wordt opgeslagen met de buildrecord of test en wordt geïmplementeerd in latere pijplijnen. Zie Artefacten voor meer informatie.

- task: CopyFiles@2
  inputs:
    contents: '**/*.apk'
    targetFolder: '$(build.artifactStagingDirectory)'
- task: PublishBuildArtifacts@1

Implementeren

App Center toevoegen

Voeg de taak App Center Distribueren toe om een toepassing te distribueren naar een groep testers of bètagebruikers, of de toepassing te promoveren naar Intune of Google Play. Er is een gratis App Center-account vereist (er is geen betaling nodig).

# App Center distribute v3
# Distribute app builds to testers and users via Visual Studio App Center.
- task: AppCenterDistribute@3
  inputs:
    serverEndpoint: # string. Required. App Center service connection. 
    appSlug: # string. Required. App slug. 
    appFile: # string. Alias: app. Required. Binary file path. 
    #buildVersion: # string. Build version. 
    releaseNotesOption: 'input' # 'input' | 'file'. Alias: releaseNotesSelection. Required. Create release notes. Default: input.
    releaseNotesInput: # string. Required when releaseNotesSelection = input. Release notes. 
    #releaseNotesFile: # string. Required when releaseNotesSelection = file. Release notes file. 
    #isMandatory: false # boolean. Require users to update to this release. Default: false.
    destinationType: 'groups' # 'groups' | 'store'. Required. Release destination. Default: groups.
    #distributionGroupId: # string. Alias: destinationGroupIds. Optional. Use when destinationType = groups. Destination IDs. 
    #destinationStoreId: # string. Required when destinationType = store. Destination ID. 
    #isSilent: # boolean. Optional. Use when destinationType = groups. Do not notify testers. Release will still be available to install. 
  # Symbols
    #symbolsOption: 'Apple' # 'Apple' | 'Android' | 'UWP'. Alias: symbolsType. Symbols type. Default: Apple.
    #symbolsPath: # string. Optional. Use when symbolsType == AndroidNative || symbolsType = Windows. Symbols path. 
    #appxsymPath: # string. Optional. Use when symbolsType = UWP. Symbols path (*.appxsym). 
    #symbolsDsymFiles: # string. Alias: dsymPath. Optional. Use when symbolsType = Apple. dSYM path. 
    #symbolsMappingTxtFile: # string. Alias: mappingTxtPath. Optional. Use when symbolsType = Android. Mapping file. 
    #nativeLibrariesPath: # string. Optional. Use when symbolsType == Android. Native Library File Path. 
    #symbolsIncludeParentDirectory: # boolean. Alias: packParentFolder. Optional. Use when symbolsType = Apple. Include all items in parent folder.

Google Play installeren

Installeer de Google Play-extensie en gebruik de volgende taken om interactie met Google Play te automatiseren. Deze taken worden standaard geverifieerd bij Google Play met behulp van een serviceverbinding die u configureert.

Vrijgeven

Voeg de Google Play Release-taak toe om een nieuwe Android-app-versie vrij te geven aan de Google Play Store.

- task: GooglePlayRelease@4
  inputs:
    apkFile: '**/*.apk'
    serviceEndpoint: 'yourGooglePlayServiceConnectionName'
    track: 'internal'

Promoten

Voeg de Google Play Promote-taak toe om een eerder uitgebrachte Android-toepassingsupdate van het ene spoor naar het andere te promoveren , zoals alphabeta.

- task: GooglePlayPromote@3
  inputs:
    packageName: 'com.yourCompany.appPackageName'
    serviceEndpoint: 'yourGooglePlayServiceConnectionName'
    sourceTrack: 'internal'
    destinationTrack: 'alpha'

Implementatie verhogen

Voeg de implementatietaak google Play-verhoging toe om het implementatiepercentage van een toepassing te verhogen die eerder voor het rollout spoor werd uitgebracht.

- task: GooglePlayIncreaseRollout@2
  inputs:
    packageName: 'com.yourCompany.appPackageName'
    serviceEndpoint: 'yourGooglePlayServiceConnectionName'
    userFraction: '0.5' # 0.0 to 1.0 (0% to 100%)

Statusupdate

Voeg de Google Play Status Update-taak toe om de implementatiestatus bij te werken voor de toepassing die eerder voor het rollout bijhouden is uitgebracht.

  - task: GooglePlayStatusUpdate@2
    inputs:
      authType: ServiceEndpoint
      packageName: 'com.yourCompany.appPackageName'
      serviceEndpoint: 'yourGooglePlayServiceConnectionName'
      status: 'inProgress' # draft | inProgress | halted | completed

Veelgestelde vragen

V: Hoe kan ik app-bundels maken?

A: U kunt uw app-bundel bouwen en ondertekenen met een inlinescript en een beveiligd bestand. Hiervoor moet u eerst uw sleutelarchief downloaden en opslaan als een beveiligd bestand in de bibliotheek. Maak vervolgens variabelen voor keystore.passworden key.passwordkey.aliasin een variabelegroep.

Gebruik vervolgens de taken Secure File en Bash downloaden om uw sleutelarchief te downloaden en uw app-bundel te bouwen en te ondertekenen.

Download in dit YAML-bestand een app.keystore beveiligd bestand en gebruik een bash-script om een app-bundel te genereren. Gebruik vervolgens Copy Files om de app-bundel te kopiëren. Maak en sla daar een artefact op met Publish Build Artifact of gebruik de Google Play-extensie om te publiceren.

- task: DownloadSecureFile@1
  name: keyStore
  displayName: "Download keystore from secure files"
  inputs:
    secureFile: app.keystore

- task: Bash@3
  displayName: "Build and sign App Bundle"
  inputs:
    targetType: "inline"
    script: |
      msbuild -restore $(Build.SourcesDirectory)/myAndroidApp/*.csproj -t:SignAndroidPackage -p:AndroidPackageFormat=aab -p:Configuration=$(buildConfiguration) -p:AndroidKeyStore=True -p:AndroidSigningKeyStore=$(keyStore.secureFilePath) -p:AndroidSigningStorePass=$(keystore.password) -p:AndroidSigningKeyAlias=$(key.alias) -p:AndroidSigningKeyPass=$(key.password)

- task: CopyFiles@2
  displayName: 'Copy deliverables'
  inputs:
    SourceFolder: '$(Build.SourcesDirectory)/myAndroidApp/bin/$(buildConfiguration)'
    Contents: '*.aab'
    TargetFolder: 'drop'