Is Cargo feasible as a (more) general-purpose package manager?


#1

Hi all,

I’ve been reading up on Cargo and it seems to me that it may be possible to use it as a package manager for more than just Rust projects. Since the manifest spec provides a means to include arbitrary files in a crate, would it be possible to roll a custom registry (akin to crates.io), and use it to manage packages of multiple languages that may depend on one another? In this use case, I would imagine a “package” to be generically defined as a collection of files with a version and a repository.

The use-case I’m imagining would be developing native libraries (using either C, C++, rust, etc) which are intended to be used from higher-level languages using Foreign Function Interfaces (FFI). For example, if I had a package that produces a native library libfoo.so and wanted to distribute a package that produces a foo.jar that provided a clean interface that wraps libfoo using some java FFI library (there are a few). If I were a java developer that wanted to use that library, listing foo.jar as a dependency should then find and include libfoo.so into the project. Then, cargo could invoke a build using a tool most native to the project being built (e.g. gradle or maven for java, make for C, npm for node.js, etc.). However, I might also want to write a node library, foo.js, which wraps the same libfoo.so, so a java-based approach that simply bundles libfoo.so into a jar wouldn’t seem to suffice.

It seems to me that Cargo in its current state is almost a superset of a tool that could achieve that scenario. I’d imagine all it would take would be to create a set of build.rs presets for invoking other build systems, and to create a new registry to serve as the “generic packages” hosting.

I’d like to hear others’ thoughts on this. Has this been done before? Are there better alternatives for accomplishing the same thing I’m after? Are there changes that could be made to cargo to somewhat decouple it from being strictly a rust utility?


#2

Some -sys packages provide an option to download and build the native dep if it doesn’t already exist, so I’d say you’re on the right track.


#3

What do you mean by -sys packages, and do you have any specific examples? I’d like to see how that’s done.


#4

http://doc.crates.io/build-script.html#case-study-building-some-native-code are the docs for it; the only difference would be a small addition to the build script that would check to see if the library exists, and if not, download hello.c and then build.

curl-sys does something like this: https://github.com/alexcrichton/curl-rust/blob/master/curl-sys/build.rs more specifically

and below


#5

I think so. If we could reasonably package every C/C++ library that C/C++ programmers wanted to use via cargo, if it got ergonomic enough that could be a compelling pathway for C/C++ programmers to get into Rust.


#6

For me Cargo is unsuitable for building anything other than a simple Rust executable, because it can’t run commands on compiled binaries. Without hacks or a help of another build system I can’t produce a .deb or .jar from Cargo:

Cargo also doesn’t manage system-wide things. It doesn’t keep cargo install-ed binaries up to date, which means they all stop working after every Rust upgrade. If you used Cargo to install system-wide libraries, jar files, etc. I imagine you’d have a similar problem.