使用CMAKE创建和激活Conda环境
我在cmakelists.txt
文件中有以下内容。我正在尝试使用cmake检查是否已安装在系统上并激活该环境的conda环境 。如果不存在环境,请创建环境并激活环境。这是假设Conda已经通过
# Create and activate a Python environment.
cmake_minimum_required(VERSION 3.18)
# Define the project
project(MyExample)
# Specify the C++ standard
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED True)
# Make sure Python is installed
find_package(Python REQUIRED)
# Activate conda environment, assume Anaconda or Miniconda is already installed
if(EXISTS /opt/miniconda3/envs/myenv)
execute_process(COMMAND conda activate myenv)
else()
execute_process(COMMAND conda create --yes --quiet --name myenv python)
execute_process(COMMAND conda activate myenv)
endif()
当我运行上述cmake文件时,我会收到错误:
CommandNotFoundError: Your shell has not been properly configured to use 'conda activate'.
但是,我的系统上安装了conda,可以在终端中手动激活环境。为什么环境不会通过CMAKE激活?
I have the following in a CMakeLists.txt
file. I'm trying to use cmake to check if a conda environment named myenv
is installed on the system and activate that environment. If the environment does not exist, then create the environment and activate it. This assumes that conda is already installed via Anaconda (or Miniconda).
# Create and activate a Python environment.
cmake_minimum_required(VERSION 3.18)
# Define the project
project(MyExample)
# Specify the C++ standard
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED True)
# Make sure Python is installed
find_package(Python REQUIRED)
# Activate conda environment, assume Anaconda or Miniconda is already installed
if(EXISTS /opt/miniconda3/envs/myenv)
execute_process(COMMAND conda activate myenv)
else()
execute_process(COMMAND conda create --yes --quiet --name myenv python)
execute_process(COMMAND conda activate myenv)
endif()
When I run the above cmake file, I get the error:
CommandNotFoundError: Your shell has not been properly configured to use 'conda activate'.
However, conda is installed on my system and I can activate the environment manually in the terminal. Why does the environment not get activated via cmake?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
第一个问题是错误消息中,这表明cmake评估
execute_process_process
命令的shell not知道什么conda激活
的意思。这可能是因为
conda Init< shell>
从未为Cmake使用的特定外壳(也许是?)运行。 此答案有一些详细信息conda Init
做什么。这也可能是因为定义conda激活
的Conda初始化代码仅在交互式外壳中加载 - 我不希望Cmake使用。bash -l -c'conda激活foo'
)中执行执行可能会有骇人听闻的方法来强制在交互式外壳( 这里的过程没有意义:CONDA环境的激活状态范围范围为外壳过程。我希望(sub)外壳在
execute_process
的完成后死亡。因此,即使激活起作用,它也不会在CMake脚本中持续存在。一般而言
,此Cmake脚本似乎不是一个好方法。将代码的汇编与用户级别的特殊命名Conda环境的存在的紧密耦合似乎违背了CMAKE的精神,该精神旨在自动化软件依赖性的发现,以便用户不需要通常的硬编码位置。也许值得重新评估试图完成的事情和实现目标的策略。
例如,在Conda Forge上,许多软件包都用CMAKE编译,但是在那里的CMake是在已经激活的环境中执行的,并且本身对Conda一无所知。这使得CMAKE代码完全不可知其提供的依赖关系,我认为这是更清洁的工程。
The first issue is in the error message, which indicates that the shell that CMake evaluates the
execute_process
command under doesn't know whatconda activate
means.This could be because
conda init <shell>
has never been run for the particular shell that CMake uses (bash, perhaps?). This answer has some details on whatconda init
does. It could also be because the Conda initialization code that definesconda activate
only gets loaded in interactive shells - which I wouldn't expect CMake to be using. There might be hacky ways to force execution in an interactive shell (bash -l -c 'conda activate foo'
), but that doesn't matter because...Even if the above were working, the procedures here don't make sense: a Conda environment's activation status is scoped to the shell process. I would expect that the (sub)shell dies with the completion of the
execute_process
. So, even if the activation worked, it wouldn't persist any further in the CMake script.Discussion
Generally, this CMake script does not seem like a good approach. Tight-coupling the compilation of code to the existence of a particularly-named Conda environment at the user level seems to go against the spirit of CMake, which aims to automate the discovery of software dependencies so that users don't need commonly hardcoded locations. Perhaps it might be worth reassessing what is trying to be accomplished and the strategy to get there.
For example, on Conda Forge, lots of packages compile with CMake, but there CMake is executed in the context of an already activated environment and itself knows nothing about Conda. This makes it so the CMake code is completely agnostic to how its dependencies are provided, which I regard as cleaner engineering.