Bagikan melalui


Menggunakan templat untuk keamanan

Layanan Azure DevOps | Azure DevOps Server 2022 | Azure DevOps Server 2020

Artikel ini menjelaskan bagaimana templat dapat menyederhanakan keamanan untuk Azure Pipelines. Templat dapat menentukan struktur luar alur Anda dan membantu mencegah infiltrasi kode berbahaya. Templat juga dapat secara otomatis menyertakan langkah-langkah untuk melakukan tugas seperti pemindaian kredensial. Jika beberapa alur dalam tim atau organisasi Anda memiliki struktur yang sama, pertimbangkan untuk menggunakan templat.

Memeriksa sumber daya yang dilindungi membentuk kerangka kerja keamanan mendasar untuk Azure Pipelines. Pemeriksaan ini berlaku terlepas dari struktur, tahapan, dan pekerjaan alur. Anda dapat menggunakan templat untuk membantu menerapkan pemeriksaan ini.

Menyertakan dan memperluas templat

Azure Pipelines menyediakan menyertakan dan memperluas templat.

  • Menyertakan templat menyertakan kode templat langsung di file luar yang mereferensikannya, mirip #include dengan C++. Contoh alur berikut menyisipkan templat include-npm-steps.yml ke dalam bagian steps .

      steps:
      - template: templates/include-npm-steps.yml 
    
  • Memperluas templat menentukan struktur luar alur dan menawarkan titik tertentu untuk kustomisasi yang ditargetkan. Dalam konteks C++, extends templat menyerupai warisan.

Saat Anda menggunakan extends templat, Anda juga dapat menggunakan includes templat dan alur akhir untuk melakukan bagian konfigurasi umum. Untuk referensi lengkap, lihat Referensi penggunaan templat.

Memperluas templat

Untuk alur yang paling aman, mulailah dengan menggunakan templat perluas. Templat ini menentukan struktur luar alur dan mencegah kode berbahaya menyusup ke alur.

Misalnya, file templat berikut diberi nama template.yml.

parameters:
- name: usersteps
  type: stepList
  default: []
steps:
- ${{ each step in parameters.usersteps }}:
  - ${{ step }}

Alur berikut memperluas templat template.yml .

# azure-pipelines.yml
resources:
  repositories:
  - repository: templates
    type: git
    name: MyProject/MyTemplates
    ref: refs/tags/v1

extends:
  template: template.yml@templates
  parameters:
    usersteps:
    - script: echo This is my first step
    - script: echo This is my second step

Tip

Saat Anda menyiapkan extends templat, pertimbangkan untuk menjangkarkannya ke cabang atau tag Git tertentu sehingga jika ada perubahan yang melanggar, alur yang ada tidak terpengaruh. Contoh sebelumnya menggunakan fitur ini.

Fitur keamanan alur YAML

Sintaks alur YAML mencakup beberapa perlindungan bawaan. Memperluas templat dapat memberlakukan penggunaannya. Untuk meningkatkan keamanan alur, Anda dapat menerapkan salah satu batasan berikut.

Target langkah

Anda dapat membatasi langkah-langkah tertentu untuk dijalankan dalam kontainer daripada pada host. Langkah-langkah dalam kontainer tidak memiliki akses ke host agen, mencegah langkah-langkah ini mengubah konfigurasi agen atau meninggalkan kode berbahaya untuk eksekusi nanti.

Misalnya, pertimbangkan untuk membatasi akses jaringan. Tanpa akses jaringan terbuka, langkah-langkah pengguna tidak dapat mengambil paket dari sumber yang tidak sah atau mengunggah kode dan rahasia ke lokasi jaringan eksternal.

Contoh alur berikut menjalankan langkah-langkah pada host agen sebelum menjalankan langkah-langkah di dalam kontainer.

resources:
  containers:
  - container: builder
    image: mysecurebuildcontainer:latest
steps:
- script: echo This step runs on the agent host, and it could use Docker commands to tear down or limit the container's network
- script: echo This step runs inside the builder container
  target: builder

Pembatasan perintah pengelogan agen

Anda dapat membatasi layanan yang disediakan agen Azure Pipelines untuk langkah-langkah pengguna. Langkah pengguna meminta layanan dengan menggunakan perintah pengelogan, yang merupakan string yang diformat khusus yang dicetak ke output standar. Dalam mode terbatas, sebagian besar layanan agen, seperti mengunggah artefak dan melampirkan hasil pengujian, tidak tersedia.

Contoh tugas berikut gagal karena propertinya target menginstruksikan agen untuk tidak mengizinkan penerbitan artefak.

- task: PublishBuildArtifacts@1
  inputs:
    artifactName: myartifacts
  target:
    commands: restricted

Dalam restricted mode, setvariable perintah tetap diizinkan, jadi perhatian diperlukan karena variabel alur diekspor sebagai variabel lingkungan ke tugas berikutnya. Jika tugas menghasilkan data yang disediakan pengguna, seperti masalah terbuka yang diambil melalui REST API, tugas tersebut mungkin rentan terhadap serangan injeksi. Konten pengguna berbahaya dapat mengatur variabel lingkungan yang mungkin dieksploitasi untuk membahayakan host agen.

Untuk mengurangi risiko ini, penulis alur dapat secara eksplisit menyatakan variabel mana yang dapat diatur dengan menggunakan perintah pengelogan setvariable . Saat Anda menentukan daftar kosong, semua pengaturan variabel tidak diizinkan.

Contoh tugas berikut gagal karena tugas hanya diizinkan untuk mengatur expectedVar variabel atau variabel yang diawali dengan ok.

- task: PowerShell@2
  target:
    commands: restricted
    settableVariables:
    - expectedVar
    - ok*
  inputs:
    targetType: 'inline'
    script: |
      Write-Host "##vso[task.setvariable variable=BadVar]myValue"

Tahap kondisi atau eksekusi pekerjaan

Anda dapat membatasi tahapan dan pekerjaan untuk dijalankan hanya dalam kondisi tertentu. Dalam contoh berikut, kondisi memastikan bahwa kode terbatas hanya dibangun untuk cabang utama.

jobs:
- job: buildNormal
  steps:
  - script: echo Building the normal, unsensitive part
- ${{ if eq(variables['Build.SourceBranchName'], 'refs/heads/main') }}:
  - job: buildMainOnly
    steps:
    - script: echo Building the restricted part that only builds for main branch

Modifikasi sintaks

Templat Azure Pipelines memiliki fleksibilitas untuk melakukan iterasi dan memodifikasi sintaks YAML. Dengan menggunakan iterasi, Anda dapat menerapkan fitur keamanan YAML tertentu.

Templat juga dapat menulis ulang langkah-langkah pengguna, yang hanya memungkinkan tugas yang disetujui untuk dijalankan. Misalnya, Anda dapat mencegah eksekusi skrip sebaris.

Contoh templat berikut mencegah jenis bashlangkah , , powershellpwsh, dan script berjalan. Untuk penguncian lengkap skrip ad-hoc, Anda juga dapat memblokir BatchScript dan ShellScript.

# template.yml
parameters:
- name: usersteps
  type: stepList
  default: []
steps:
- ${{ each step in parameters.usersteps }}:
  - ${{ if not(or(startsWith(step.task, 'Bash'),startsWith(step.task, 'CmdLine'),startsWith(step.task, 'PowerShell'))) }}:  
    - ${{ step }}
  # The following lines replace tasks like Bash@3, CmdLine@2, PowerShell@2
  - ${{ else }}:  
    - ${{ each pair in step }}:
        ${{ if eq(pair.key, 'inputs') }}:
          inputs:
            ${{ each attribute in pair.value }}:
              ${{ if eq(attribute.key, 'script') }}:
                script: echo "Script removed by template"
              ${{ else }}:
                ${{ attribute.key }}: ${{ attribute.value }}
        ${{ elseif ne(pair.key, 'displayName') }}:
          ${{ pair.key }}: ${{ pair.value }}

          displayName: 'Disabled by template: ${{ step.displayName }}'

Dalam alur berikut yang memperluas templat ini, langkah-langkah skrip dilucuti dan tidak dijalankan.

# azure-pipelines.yml
extends:
  template: template.yml
  parameters:
    usersteps:
    - task: MyTask@1
    - script: echo This step will be stripped out and not run!
    - bash: echo This step will be stripped out and not run!
    - powershell: echo "This step will be stripped out and not run!"
    - pwsh: echo "This step will be stripped out and not run!"
    - script: echo This step will be stripped out and not run!
    - task: CmdLine@2
      displayName: Test - Will be stripped out
      inputs:
        script: echo This step will be stripped out and not run!
    - task: MyOtherTask@2

Parameter jenis aman

Sebelum alur berjalan, templat dan parameternya diubah menjadi konstanta. Parameter templat dapat meningkatkan keamanan jenis untuk parameter input.

Dalam contoh templat berikut, parameter membatasi opsi kumpulan alur yang tersedia dengan memberikan enumerasi pilihan tertentu alih-alih mengizinkan string bentuk bebas.

# template.yml
parameters:
- name: userpool
  type: string
  default: Azure Pipelines
  values:
  - Azure Pipelines
  - private-pool-1
  - private-pool-2

pool: ${{ parameters.userpool }}
steps:
- script: # ... removed for clarity

Saat alur memperluas templat, alur harus menentukan salah satu pilihan kumpulan yang tersedia.

# azure-pipelines.yml
extends:
  template: template.yml
  parameters:
    userpool: private-pool-1

Langkah-langkah templat

Templat dapat secara otomatis menyertakan langkah-langkah dalam alur. Langkah-langkah ini dapat melakukan tugas seperti pemindaian kredensial atau pemeriksaan kode statis. Templat berikut menyisipkan langkah-langkah sebelum dan sesudah langkah-langkah pengguna di setiap pekerjaan.

parameters:
  jobs: []

jobs:
- ${{ each job in parameters.jobs }}: 
  - ${{ each pair in job }}:  
      ${{ if ne(pair.key, 'steps') }}:
        ${{ pair.key }}: ${{ pair.value }}
    steps:                            
    - task: CredScan@1 
    - ${{ job.steps }} 
    - task: PublishMyTelemetry@1 
      condition: always()

Penegakan templat

Templat adalah mekanisme keamanan yang berharga, tetapi efektivitasnya bergantung pada penegakan. Titik kontrol utama untuk memberlakukan penggunaan templat adalah sumber daya yang dilindungi. Anda dapat mengonfigurasi persetujuan dan pemeriksaan untuk kumpulan agen anda atau sumber daya lain yang dilindungi seperti repositori. Misalnya, lihat Menambahkan pemeriksaan sumber daya repositori.

Templat yang diperlukan

Untuk menerapkan penggunaan templat tertentu, konfigurasikan pemeriksaan templat yang diperlukan untuk sumber daya. Pemeriksaan ini hanya berlaku ketika alur meluas dari templat.

Saat Anda melihat pekerjaan alur, Anda dapat memantau status pemeriksaan. Jika alur tidak diperluas dari templat yang diperlukan, pemeriksaan gagal. Eksekusi berhenti dan memberi tahu Anda tentang pemeriksaan yang gagal.

Cuplikan layar memperlihatkan pemeriksaan persetujuan yang gagal.

Saat Anda menggunakan templat yang diperlukan, pemeriksaan akan lolos.

Cuplikan layar memperlihatkan pemeriksaan persetujuan yang diteruskan.

Templat params.yml berikut harus dirujuk dalam alur apa pun yang memperluasnya.

# params.yml
parameters:
- name: yesNo 
  type: boolean
  default: false
- name: image
  displayName: Pool Image
  type: string
  default: ubuntu-latest
  values:
  - windows-latest
  - ubuntu-latest
  - macOS-latest

steps:
- script: echo ${{ parameters.yesNo }}
- script: echo ${{ parameters.image }}

Contoh alur berikut memperluas templat params.yml dan memerlukannya untuk disetujui. Untuk menunjukkan kegagalan alur, komentari referensi ke params.yml.

# azure-pipeline.yml

resources:
 containers:
     - container: my-container
       endpoint: my-service-connection
       image: mycontainerimages

extends:
    template: params.yml
    parameters:
        yesNo: true
        image: 'windows-latest'