Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Option to exclude or ignore specific artifacts #503

Open
Tim203 opened this issue Dec 2, 2022 · 2 comments
Open

Option to exclude or ignore specific artifacts #503

Tim203 opened this issue Dec 2, 2022 · 2 comments

Comments

@Tim203
Copy link

Tim203 commented Dec 2, 2022

First of all, thank you for creating Rustler! I really enjoy using it.

I have a Cargo.toml that looks something like this:

[package]
name = "name"

[lib]
name = "name"
path = "src/lib.rs"
crate-type = ["cdylib"]

[[bin]]
name = "name-bin"
path = "src/main.rs"
required-features = ["build-binary"]

I use the lib artifact in my Elixir code, and I use the bin artifact to debug the lib with some GUI stuff that's not needed in the lib artifact (prevents fetching and compiling unneeded dependencies).

Once it has successfully compiled, Rustler tries to copy all artifacts:

** (File.CopyError) could not copy from "/app/_build/prod/lib/xx/native/name/release/name-bin" to "priv/native/name-bin": no such file or directory
    (elixir 1.14.0) lib/file.ex:838: File.cp!/3
    (elixir 1.14.0) lib/enum.ex:975: Enum."-each/2-lists^foreach/1-0-"/2
    (rustler 0.26.0) lib/rustler/compiler.ex:44: Rustler.Compiler.compile_crate/2
    ...

This is not desired because I only need the lib, which has successfully compiled.
Instead, my build failed because not every artifact was compiled.

Related Rustler code:
https://github.com/rusterlium/rustler/blob/rustler-0.26.0/rustler_mix/lib/rustler/compiler.ex#L178
https://github.com/rusterlium/rustler/blob/rustler-0.26.0/rustler_mix/lib/rustler/compiler.ex#L197

My personal preference would go to a solution like this: Continue to try to copy all possible artifacts, but give a warning instead of halting the Rustler compile process when a specific artifact doesn't exist (but maybe require at least one artifact per package?).
I'm also ok with a solution that allows people to exclude/include specific artifacts.

@evnu
Copy link
Member

evnu commented Dec 5, 2022

Thanks for the report. I'd like to understand your use-case a little better. You explicitly don't want to build the binary usually and use a feature to disable building it?

Continue to try to copy all possible artifacts, but give a warning instead of halting the Rustler compile process when a specific artifact doesn't exist (but maybe require at least one artifact per package?).

I am hesitant with implementing a heuristic to determine if compilation succeeded. Compilation should be ideally all-or-nothing.

I'm also ok with a solution that allows people to exclude/include specific artifacts.

Something like exclude_binaries: [bin1, bin2], or rather only_build: "name"? Note: rustler is mostly concerned with NIFs, so I would expect that it builds at least a library. We could try to exclude non-libraries from building, or add an option to do just that (:only_build_lib).

@Tim203
Copy link
Author

Tim203 commented Dec 17, 2022

You explicitly don't want to build the binary usually and use a feature to disable building it?

Yes. The project only needs the library. The binary contains some additional stuff that's only interesting for development purposes. The binary can run as a standalone GUI application while the library depends on Rustler. I guess I could abstract the Rustler code from the library to another binary, but then the same problem will remain as Rustler tries to assert the existence of all possible artifacts.

This is my first project in Rust, so I'm still new to how the build system works. I run the binary inside IntelliJ and all I know is that when I'm compiling my Elixir project it only tries to compile the library. I use required features to include some dependencies in the binary while excluding them from the library.

Something like exclude_binaries: [bin1, bin2], or rather only_build: "name"?

That should do the trick yeah. However, the latter might be too restrictive for other projects.
Perhaps both an exclude_binaries and an include_binaries would be better?
include_binaries would filter out all binaries that don't match their entries and exclude_binaries would filter out all binaries that do match their entries.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants