You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Bindgen code from objective-c categories results in traits like CLASS_CATEGORY to be generated. This is not intuitive for a few reasons:
I didn't even realize that bindgen supported categories. I was allowlisting the classes I wanted and saw that methods were missing. I looked in the files and realized that those methods were in category blocks and just assumed that it was unsupported. Only later did I realize that I had to allowlist CLASS_CATEGORY (or more broadly CLASS_.*).
Category names (and contents!) are implementation details. They are used in the implementation to organize things but are not exposed in any way in normal objective-c APIs. Creating a separate rust API is an unfortunate mismatch for developers.
Because the categories are traits, you need to import them by name. I'd prefer not to use use my_crate_bindings::* to pull in all the category traits, so I need to know their names to import them.
This is a tricky problem to work around, but if there is some way to address some of these points it'd make the developer interaction with the generated code more similar to the interaction when using objective-c.
use my_crate_bindings::{Foo,IFoo,Foo_BarCategory};let f = Foo::alloc();unsafe{ f.categoryMethod()};
Expected Results
I'm not entirely sure the best approach, but some suggestions:
Maybe allowlist_item("Class") can include categories automatically? I figure this is somewhat unlikely given that the allowlist acts on the rust API.
Change all categories into impl Foo instead. This is how I expected bindgen to work, though it doesn't mesh well with inheritance (see Objective-c categories aren't included in inheritance traits and impl blocks #1779) and then the trait IFoo might seem weird. I don't think there's a strict need to keep them separate given that categories are invisible in the objective-c API and exist purely in syntax. Alternatively you could merge all included categories into the one trait IFoo (and then inheritance will work, at the cost of what I imagine would be a bit more juggling in the bindgen logic).
Put all category traits into a module (either as a whole for everything generated or for each class). For example, I would be much less hesitant to use my_crate_bindings::{Foo, FooCategories::*}. This avoids my needing to know the category names, though I still need to be aware of how bindgen implements categories.
The text was updated successfully, but these errors were encountered:
This is not a bad idea. I've been tempted to try this. One thing I'd say is that this will result in a much bigger generated source. Take for example these uikit-sys bindings. It's been a while since I've generated them but IIRC, the generated rust was ~100k to ~300k lines of rust and took a few minutes to compile - it was all in one file and I don't think that can be parallelized. Admittedly, it also generates all the stuff for Foundation. The CIImageProvider category of NSObject for example has a lot of implementers.
Bindgen code from objective-c categories results in traits like
CLASS_CATEGORY
to be generated. This is not intuitive for a few reasons:CLASS_CATEGORY
(or more broadlyCLASS_.*
).use my_crate_bindings::*
to pull in all the category traits, so I need to know their names to import them.This is a tricky problem to work around, but if there is some way to address some of these points it'd make the developer interaction with the generated code more similar to the interaction when using objective-c.
Input C/C++ Header
Bindgen Invocation
Actual Results
And in code using the generated code:
Expected Results
I'm not entirely sure the best approach, but some suggestions:
allowlist_item("Class")
can include categories automatically? I figure this is somewhat unlikely given that the allowlist acts on the rust API.impl Foo
instead. This is how I expected bindgen to work, though it doesn't mesh well with inheritance (see Objective-c categories aren't included in inheritance traits and impl blocks #1779) and then thetrait IFoo
might seem weird. I don't think there's a strict need to keep them separate given that categories are invisible in the objective-c API and exist purely in syntax. Alternatively you could merge all included categories into the onetrait IFoo
(and then inheritance will work, at the cost of what I imagine would be a bit more juggling in the bindgen logic).use my_crate_bindings::{Foo, FooCategories::*}
. This avoids my needing to know the category names, though I still need to be aware of how bindgen implements categories.The text was updated successfully, but these errors were encountered: