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

Combine generated .swift and headers file? #2257

Open
praveenperera opened this issue Oct 6, 2024 · 10 comments
Open

Combine generated .swift and headers file? #2257

praveenperera opened this issue Oct 6, 2024 · 10 comments

Comments

@praveenperera
Copy link
Contributor

praveenperera commented Oct 6, 2024

I have a project called cove that is using uniffi, I had it set up as a single crate and the build script calling cargo run --bin uniffi-bindgen generate --library ./target/debug/libcove.dylib --language swift --out-dir ./bindings

This outputs Cove.swift, modulemap and headers file, which I then use to make a xcframework.

I wanted to see if I could make new functionality in a crate, so I made one called cove_nfc all using proc macros and then in cove/src/lib.rs I have

uniffi::setup_scaffolding!();
cove_nfc::uniffi_reexport_scaffolding!();

That all seems to work fine, but when I run the uniffi-bindgen it now makes separate swift files, headers and module maps for cove and cove_nfc.

Is it possible to just combine them?

@mhammond
Copy link
Member

mhammond commented Oct 7, 2024

The usual way to do this is to have both your crates in the same library - we don't support any multi-lib scenarios.

@praveenperera
Copy link
Contributor Author

praveenperera commented Oct 7, 2024

Cove is my main library and I was hoping to split off other functionality into other crates, that Cove could then depend one. Is that not possible to do that and still only have one set of outputs (shared dylib, .swift and headers)?

Would it make more sense to still add the proc macros in a crate for the structs and enums, but do all the [#uniffi::exports] in my main crate?

Would that accomplish what I want?

I tried to do that but got this error:

unknown throw type: Some(External { module_path: "cove_nfc", name: "NfcReaderError", namespace: "cove_nfc", kind: DataClass, tagged: false })

@mhammond
Copy link
Member

mhammond commented Oct 7, 2024

Cove is my main library and I was hoping to split off other functionality into other crates, that Cove could then depend one.

That's possible, but it happens at build-time. Each of these other crates would end up building its own dylib which includes Cove. You don't need multiple dylibs for uniffi projects because Rust doesn't support them.

@praveenperera
Copy link
Contributor Author

praveenperera commented Oct 7, 2024

That's possible, but it happens at build-time. Each of these other crates would end up building its own dylib which includes Cove. You don't need multiple dylibs for uniffi projects because Rust doesn't support them.

I see thank you, I think I'll close this issue then, because when I try to do that I'm getting this issue now:

unknown throw type: Some(External { module_path: "cove_nfc", name: "NfcReaderError", namespace: "cove_nfc", kind: DataClass, tagged: false })

Same as #2225

I'll try to explore a bit more about why that is an maybe make a new issue. I'm wondering if its because of the weird way I have the crates set up now for ease of use.

My folder structure is

rust
  cove (non workspace crate)
    src/lib/
    Cargo.toml
    Cargo.lock
  cove_crates (different workspace crate)
    cove_nfc/ (crate i'm trying to import)
      src/lib/
    Cargo.toml
    Cargo.lock

It's non standard, and probably messing with how uniffi searches for deps.

@Alphapage
Copy link

As far as I tried, it seems to only happen when using

#[derive(uniffi::Error, Debug)]
pub enum MyError {}

So you can use multiple libraries, but all errors must be in the main lib.
Is it a limitation ? Or a bug ?

@praveenperera
Copy link
Contributor Author

@Alphapage i haven’t had a chance to try it with a more normal setup but if it only happens with errors it sounds like it could be a bug?

Do you have a repo that you tested this on?

@Alphapage
Copy link

Alphapage commented Oct 14, 2024

Sorry, but I don't have a repo to share.
The only thing I can tell is as soon as I removed all #[derive(uniffi::Error, Debug)] from my dependent library and put it back to main library, then it started working like a charm.
So, it seems uniffi::Error or more globally enums aren't supported in a child library :-(

@praveenperera
Copy link
Contributor Author

When one of us gets a chance, lets make a minimal repo and make a new issue, cc: @mhammond ^

@mhammond
Copy link
Member

Probably #2265 - we don't yet support errors defined in another crate.

@praveenperera
Copy link
Contributor Author

@mhammond I'm going to re-open this because I tried doing this with a more traditional crate structure but I'm still not sure the best way to use other crates in my main crate.

My main crate / library is cove: https://github.com/bitcoinppl/cove

And I am trying to use this crate in it, that crate has uniffi under a feature.

When I compile the rust and run uniffi-bindgen it all works fine. But the iOS app won't compile. That's because the glue code for pubport is in its own files pubport.swift, pubporFFI.h and pubportFFI.modulemap

I'm not sure what the best way to combine these with my existing cove.swift header and module map files is.

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

3 participants