diff options
| author | Joseph Hunkeler <jhunkeler@gmail.com> | 2026-06-12 13:46:41 -0400 |
|---|---|---|
| committer | Joseph Hunkeler <jhunkeler@gmail.com> | 2026-06-12 13:46:41 -0400 |
| commit | 3fdd468551b77d2c71d6fb110f16ed847abcddb8 (patch) | |
| tree | 6ce4fd62a0521e96545385da820a693093ce01f0 /src | |
| parent | 024a7bf4978f7aeccbbb5b31e52cb4126b70335b (diff) | |
| download | stasis-3fdd468551b77d2c71d6fb110f16ed847abcddb8.tar.gz | |
Add python_importlib_metadata_version function
* Use it for conda and libmamapy version detection
Diffstat (limited to 'src')
| -rw-r--r-- | src/lib/core/conda.c | 46 | ||||
| -rw-r--r-- | src/lib/core/include/conda.h | 18 |
2 files changed, 46 insertions, 18 deletions
diff --git a/src/lib/core/conda.c b/src/lib/core/conda.c index 6e9389f..b94824e 100644 --- a/src/lib/core/conda.c +++ b/src/lib/core/conda.c @@ -136,6 +136,31 @@ int pip_exec(const char *args) { return result; } +char *python_importlib_metadata_version(const char *package_name) { + int status = 0; + char cmd[PATH_MAX] = {0}; + + if (strpbrk(package_name, "\\/*{}()|;&\"'\r\n")) { + SYSERROR("package name is invalid: '%s'", package_name); + return NULL; + } + snprintf(cmd, sizeof(cmd), "python3 -c 'from importlib.metadata import version; print(version(r\x22%s\x22))'", package_name); + + char *version = shell_output(cmd, &status); + if (status) { + SYSERROR("version detection failed"); + guard_free(version); + return NULL; + } + if (!version) { + SYSERROR("unable to allocate version"); + return NULL; + } + strip(version); + return version; +} + + static const char *PKG_ERROR_STR[] = { "success", "[internal] unhandled package manager mode", @@ -739,33 +764,18 @@ int conda_capable(struct CondaCapabilities *ccap) { } if (cc->available) { - int status = 0; - char *conda_version = shell_output("python3 -c 'import conda; print(conda._version.__version__)'", &status); - if (status) { - SYSERROR("conda version detection failed"); - guard_free(conda_version); - return -1; - } + char *conda_version = python_importlib_metadata_version("conda"); if (!conda_version) { - SYSERROR("unable to allocate conda_version_raw"); + SYSERROR("conda version detection failed"); return -1; } - strip(conda_version); - char *mamba_version = shell_output("python3 -c 'import libmambapy; print(libmambapy.version.__version__)'", &status); - if (status) { - SYSERROR("mamba version detection failed"); - guard_free(conda_version); - guard_free(mamba_version); - return -1; - } + char *mamba_version = python_importlib_metadata_version("libmambapy"); if (!mamba_version) { SYSERROR("unable to allocate mamba_version"); guard_free(conda_version); - guard_free(mamba_version); return -1; } - strip(mamba_version); cc->conda_version = strdup(conda_version); cc->mamba_version = strdup(mamba_version); diff --git a/src/lib/core/include/conda.h b/src/lib/core/include/conda.h index 2d96f56..19f5d07 100644 --- a/src/lib/core/include/conda.h +++ b/src/lib/core/include/conda.h @@ -113,6 +113,24 @@ int python_exec(const char *args); int pip_exec(const char *args); /** + * Use importlib to resolve the version of an installed package + * + * ```c + * char *numpy_version = python_importlib_metadata_version("numpy"); + * if (!numpy_version) { + * fprintf(stderr, "failed to get numpy version\n"); + * exit(1); + * } + * + * printf("numpy version: %s\n", numpy_version); + * free(numpy_version); + * ``` + * @param package_name of installed python package + * @return + */ +char *python_importlib_metadata_version(const char *package_name); + +/** * Execute conda (or if possible, mamba) * Conda/Mamba is determined by PATH * |
