无法在 Azure DevOps 管道中激活 conda

Posted

技术标签:

【中文标题】无法在 Azure DevOps 管道中激活 conda【英文标题】:Fail to active conda in Azure DevOps pipeline 【发布时间】:2020-07-30 22:32:44 【问题描述】:

在 conda 构建的 python 项目上测试 azure devops 管道

jobs:
  - job: pre_build_setup
    displayName: Pre Build Setup
    pool:
      vmImage: 'ubuntu-18.04'
    steps:
      - bash: echo "##vso[task.prependpath]$CONDA/bin"
        displayName: Add conda to PATH

  - job: build_environment
    displayName: Build Environment
    dependsOn: pre_build_setup
    steps:
      - script: conda env create --file environment.yml --name build_env
        displayName: Create Anaconda environment
      - script: conda env list
        displayName:  environment installation verification

  - job: unit_tests
    displayName: Unit Tests
    dependsOn: build_environment
    strategy:
      maxParallel: 2
    steps:
      - bash: conda activate build_env

最后一步 - bash: conda activate build_env 对我失败并出现以下错误

Script contents:
conda activate build_env
========================== Starting Command Output ===========================
/bin/bash --noprofile --norc /home/vsts/work/_temp/d5af1b5c-9135-4984-ab16-72b82c91c329.sh

CommandNotFoundError: Your shell has not been properly configured to use 'conda activate'.
To initialize your shell, run

    $ conda init <SHELL_NAME>

Currently supported shells are:
  - bash
  - fish
  - tcsh
  - xonsh
  - zsh
  - powershell

See 'conda init --help' for more information and options.

IMPORTANT: You may need to close and restart your shell after running 'conda init'.


##[error]Bash exited with code '1'.
Finishing: Bash

如何激活 conda?好像路径不对,所以找不到conda。

【问题讨论】:

【参考方案1】:

CommandNotFoundError:您的 shell 未正确配置为 使用“conda 激活”。

这里的问题是您的脚本在子 shell 中运行,但 conda尚未在此子 shell 中初始化。

您需要将 active 脚本更改为:

steps:
  - task: Bash@3
    inputs:
      targetType: 'inline'
      script: |
        eval "$(conda shell.bash hook)"
        conda activate build_env
    displayName: Active

另外,请不要将Add PATHcreate environmentactive the environment 拆分为不同的作业。

对于 Azure devops 管道,agent job 是管道运行过程的基本单元,每个代理作业都有自己独立的运行环境和工作逻辑。

更详细地说,您使用 托管代理 在此问题场景中应用您的脚本。

当有一个代理作业开始运行时,我们的池系统将为该代理作业分配一个虚拟机。并且,一旦代理作业完成,此 VM 将被回收回来。当下一个代理作业开始运行时,一个全新的虚拟机将被随机重新分配。

dependsOn 只能在作业之间共享文件和传递变量。它不能让虚拟机继续下一个工作。

相信你应该能猜到你会遇到什么问题。是的,即使您可以成功应用该activate 脚本,您也将继续面对另一个error: Could not find conda environment: build_env。那是因为这个activate脚本使用的环境是全新的虚拟机,之前build_environment作业使用的虚拟机已经被系统回收了。

因此,不要将创建环境拆分为 2 个代理作业:

  - job: build_environment
    displayName: Build Environment
    dependsOn: pre_build_setup
    steps:
      - script: conda env create --file environment.yml --name build_env
        displayName: Create Anaconda environment
      - script: conda env list
        displayName:  environment installation verification
      - task: Bash@3
        inputs:
          targetType: 'inline'
          script: |
            eval "$(conda shell.bash hook)"
            conda activate build_env
        displayName: Active

【讨论】:

为什么eval "$(conda shell.bash hook)" 工作但conda init bash 失败? 你知道windows上eval "$(conda shell.bash hook)"的等价物吗? 使用-bash: 代替-script:,然后eval "$(conda shell.bash hook)" 也可以在Windows 上工作。只是一种解决方法,而不是实际的解决方案。 @CiaranWelsh 有趣。最后想想我确保我开始每个脚本都调用/full/path/to/conda init &amp;&amp; . ~/.bashrc(或Windows等效) 这太荒谬了。在过去的 3 年里,我一直在摸索如何正确地做到这一点。没有稳健的流程,只有“变通办法”。

以上是关于无法在 Azure DevOps 管道中激活 conda的主要内容,如果未能解决你的问题,请参考以下文章

Azure DevOps 项目管道无法从不同项目中的工件源访问 NuGet 包

在 Azure DevOps 中使用构建管道运行 Google 测试

从 azure devops 管道更新变量组

发布管道 Azure Devops 代码覆盖率报告

Azure Devops - 无法构建从 vs2017-win2016 到 windows-latest 的管道代理

用于运行进程的 Azure DevOps 管道