summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorruki <[email protected]>2021-04-04 12:40:37 +0800
committerruki <[email protected]>2021-04-04 12:40:37 +0800
commit93a0365566033a0dbe51a9d95ae5de75e7a63100 (patch)
tree76044eeebe98b9f148745da33b1b9fd2b1cc6900
parent21052681ba861f6b5682680f8ad9ccd0384241b6 (diff)
support to install conda packages
-rw-r--r--CHANGELOG.md2
-rw-r--r--README.md1
-rw-r--r--README_zh.md1
-rw-r--r--xmake/modules/package/manager/conda/find_package.lua162
-rw-r--r--xmake/modules/package/manager/conda/install_package.lua55
5 files changed, 221 insertions, 0 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 07cdebea0..0abcdf601 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -12,6 +12,7 @@
* [#1268](https://github.com/xmake-io/xmake/issues/1268): Add `utils.install.pkgconfig_importfiles` rule to install `*.pc` import file
* [#1268](https://github.com/xmake-io/xmake/issues/1268): Add `utils.install.cmake_importfiles` rule to install `*.cmake` import files
* [#348](https://github.com/xmake-io/xmake-repo/pull/348): Add `platform.longpaths` policy to support git longpaths
+* [#1314](https://github.com/xmake-io/xmake/issues/1314): Support to install and use conda packages
### Change
@@ -969,6 +970,7 @@
* [#1268](https://github.com/xmake-io/xmake/issues/1268): 添加 `utils.install.pkgconfig_importfiles` 规则去安装 `*.pc` 文件
* [#1268](https://github.com/xmake-io/xmake/issues/1268): 添加 `utils.install.cmake_importfiles` 规则去安装 `*.cmake` 导入文件
* [#348](https://github.com/xmake-io/xmake-repo/pull/348): 添加 `platform.longpaths` 策略去支持 git longpaths
+* [#1314](https://github.com/xmake-io/xmake/issues/1314): 支持安装使用 conda 包
## 改进
diff --git a/README.md b/README.md
index 396244d6a..d91f79149 100644
--- a/README.md
+++ b/README.md
@@ -169,6 +169,7 @@ The test project: [xmake-core](https://github.com/xmake-io/xmake/tree/master/cor
* Official package manager [Xrepo](https://github.com/xmake-io/xrepo)
* [User-built repositories](https://xmake.io/#/package/remote_package?id=using-self-built-private-package-repository)
* Conan (conan::openssl/1.1.1g)
+* Conda (conda::libpng 1.3.67)
* Vcpkg (vcpkg:ffmpeg)
* Homebrew/Linuxbrew (brew::pcre2/libpcre2-8)
* Pacman on archlinux/msys2 (pacman::libcurl)
diff --git a/README_zh.md b/README_zh.md
index db517f0eb..9b334eaab 100644
--- a/README_zh.md
+++ b/README_zh.md
@@ -178,6 +178,7 @@ $ xmake f --menu
* 官方包管理器 [Xrepo](https://github.com/xmake-io/xrepo)
* [用户自建仓库](https://xmake.io/#/zh-cn/package/remote_package?id=%e4%bd%bf%e7%94%a8%e8%87%aa%e5%bb%ba%e7%a7%81%e6%9c%89%e5%8c%85%e4%bb%93%e5%ba%93)
* Conan (conan::openssl/1.1.1g)
+* Conda (conda::libpng 1.3.67)
* Vcpkg (vcpkg:ffmpeg)
* Homebrew/Linuxbrew (brew::pcre2/libpcre2-8)
* Pacman on archlinux/msys2 (pacman::libcurl)
diff --git a/xmake/modules/package/manager/conda/find_package.lua b/xmake/modules/package/manager/conda/find_package.lua
new file mode 100644
index 000000000..77d531f9b
--- /dev/null
+++ b/xmake/modules/package/manager/conda/find_package.lua
@@ -0,0 +1,162 @@
+--!A cross-platform build utility based on Lua
+--
+-- Licensed under the Apache License, Version 2.0 (the "License");
+-- you may not use this file except in compliance with the License.
+-- You may obtain a copy of the License at
+--
+-- http://www.apache.org/licenses/LICENSE-2.0
+--
+-- Unless required by applicable law or agreed to in writing, software
+-- distributed under the License is distributed on an "AS IS" BASIS,
+-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-- See the License for the specific language governing permissions and
+-- limitations under the License.
+--
+-- Copyright (C) 2015-present, TBOOX Open Source Group.
+--
+-- @author ruki
+-- @file find_package.lua
+--
+
+-- imports
+import("core.base.json")
+import("core.base.option")
+import("core.project.config")
+import("core.project.target")
+import("lib.detect.find_tool")
+
+-- get conda prefix directory
+function _conda_prefixdir(conda)
+ local prefixdir = _g.prefixdir
+ if prefixdir == nil then
+ prefixdir = os.getenv("CONDA_PREFIX")
+ if not prefixdir then
+ local info = try {function () return os.iorunv(conda.program, {"info"}) end}
+ if info then
+ for _, line in ipairs(info:split('\n', {plain = true})) do
+ if line:find("base environment") then
+ prefixdir = line:match("ase environment : (.-) %(writable%)")
+ if prefixdir then
+ prefixdir = prefixdir:trim()
+ end
+ break
+ end
+ end
+ end
+ end
+ _g.prefixdir = prefixdir
+ end
+ return prefixdir
+end
+
+-- find package using the conda package manager
+--
+-- @param name the package name
+-- @param opt the options, e.g. {verbose = true, version = "1.12.0")
+--
+function main(name, opt)
+
+ -- check
+ opt = opt or {}
+ if not is_host(opt.plat) or os.arch() ~= opt.arch then
+ return
+ end
+
+ -- find conda
+ local conda = find_tool("conda")
+ if not conda then
+ raise("conda not found!")
+ end
+
+ -- find package
+ local version, build
+ local listinfo = try {function () return os.iorunv(conda.program, {"list", name}) end}
+ if listinfo then
+ for _, line in ipairs(listinfo:split('\n', {plain = true})) do
+ if line:startswith(name) then
+ version, build = listinfo:match(name .. "%s-([%w%.%d%-%+]+)%s-([%w%d_]+)")
+ if version and build then
+ break
+ end
+ end
+ end
+ end
+ if not version or not build then
+ return
+ end
+ if opt.require_version and opt.require_version:find('.', 1, true) and opt.require_version ~= version then
+ return
+ end
+
+ -- get meta info of package
+ -- e.g. ~/miniconda2/conda-meta/libpng-1.6.37-ha441bb4_0.json
+ local prefixdir = _conda_prefixdir(conda)
+ if not prefixdir then
+ return
+ end
+ local metafile = path.join(prefixdir, "conda-meta", name .. "-" .. version .. "-" .. build .. ".json")
+ if not os.isfile(metafile) then
+ return
+ end
+ local metainfo = json.loadfile(metafile)
+ if not metainfo or not metainfo.extracted_package_dir then
+ return
+ end
+
+ -- save includedirs, linkdirs and links
+ local result = nil
+ local packagedir = metainfo.extracted_package_dir
+ for _, line in ipairs(metainfo.files) do
+ line = line:trim()
+ if plat == "windows" then
+ line = line:lower()
+ end
+
+ -- get includedirs
+ local pos = line:find("include/", 1, true)
+ if pos then
+ result = result or {}
+ result.includedirs = result.includedirs or {}
+ table.insert(result.includedirs, path.join(packagedir, line:sub(1, pos + 7)))
+ end
+
+ -- get linkdirs and links
+ if line:endswith(".lib") or line:endswith(".a") or line:endswith(".so") or line:endswith(".dylib") then
+ result = result or {}
+ result.links = result.links or {}
+ result.linkdirs = result.linkdirs or {}
+ result.libfiles = result.libfiles or {}
+ table.insert(result.linkdirs, path.join(packagedir, path.directory(line)))
+ table.insert(result.links, target.linkname(path.filename(line)))
+ table.insert(result.libfiles, path.join(packagedir, path.directory(line), path.filename(line)))
+ end
+
+ -- add shared library directory (/bin/) to linkdirs for running with PATH on windows
+ if plat == "windows" and line:endswith(".dll") then
+ result = result or {}
+ result.linkdirs = result.linkdirs or {}
+ result.libfiles = result.libfiles or {}
+ table.insert(result.linkdirs, path.join(packagedir, path.directory(line)))
+ table.insert(result.libfiles, path.join(packagedir, path.directory(line), path.filename(line)))
+ end
+ end
+
+ -- save version
+ if result then
+ result.version = metainfo.version or version
+ end
+
+ -- remove repeat
+ if result then
+ if result.links then
+ result.links = table.unique(result.links)
+ end
+ if result.linkdirs then
+ result.linkdirs = table.unique(result.linkdirs)
+ end
+ if result.includedirs then
+ result.includedirs = table.unique(result.includedirs)
+ end
+ end
+ return result
+end
diff --git a/xmake/modules/package/manager/conda/install_package.lua b/xmake/modules/package/manager/conda/install_package.lua
new file mode 100644
index 000000000..fd37a4768
--- /dev/null
+++ b/xmake/modules/package/manager/conda/install_package.lua
@@ -0,0 +1,55 @@
+--!A cross-platform build utility based on Lua
+--
+-- Licensed under the Apache License, Version 2.0 (the "License");
+-- you may not use this file except in compliance with the License.
+-- You may obtain a copy of the License at
+--
+-- http://www.apache.org/licenses/LICENSE-2.0
+--
+-- Unless required by applicable law or agreed to in writing, software
+-- distributed under the License is distributed on an "AS IS" BASIS,
+-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+-- See the License for the specific language governing permissions and
+-- limitations under the License.
+--
+-- Copyright (C) 2015-present, TBOOX Open Source Group.
+--
+-- @author ruki
+-- @file install_package.lua
+--
+
+-- imports
+import("core.base.option")
+import("core.project.config")
+import("lib.detect.find_tool")
+
+-- install package
+--
+-- @param name the package name, e.g. conda::libpng 1.6.37
+-- @param opt the options, e.g. { verbose = true }
+--
+-- @return true or false
+--
+function main(name, opt)
+
+ -- check
+ opt = opt or {}
+ assert(is_host(opt.plat) and os.arch() == opt.arch, "conda cannot install %s for %s/%s", name, opt.plat, opt.arch)
+
+ -- find conda
+ local conda = find_tool("conda")
+ if not conda then
+ raise("conda not found!")
+ end
+
+ -- install package
+ local argv = {"install", "-y"}
+ if option.get("verbose") then
+ table.insert(argv, "-v")
+ end
+ if opt.require_version and opt.require_version:find('.', 1, true) then
+ name = name .. "=" .. opt.require_version
+ end
+ table.insert(argv, name)
+ os.vrunv(conda.program, argv)
+end