Export Display trait on errors#1021
Conversation
|
@thunderbiscuit This is ineresting for the swift side I can see the difference this is making. For kotlin, are you saying we will have to implement a custom display method (Just to clarify). Edit - I guess not cause that will then affect all bindings. |
|
Concept ACK |
| } | ||
|
|
||
| #[derive(Debug, thiserror::Error, uniffi::Error)] | ||
| #[uniffi::export(Debug, Display)] |
There was a problem hiding this comment.
Since the PR title/changelog describe exporting Display on errors broadly, should this export be applied to the other uniffi::Error enums in this file too, or should the PR scope be narrowed to CreateWithPersistError only? Right now this is the only error type getting Debug/Display exported to the bindings.
There was a problem hiding this comment.
Yep I should add it for all errors! Initially I just wanted to open this up for discussion and write up the PR description going into details. But now I'm ready to add it everywhere and will push to this PR soon.
There was a problem hiding this comment.
Thanks for updating this to cover the other error enums too, that addresses the scope question from my earlier review.
One follow-up question: should this PR add at least one binding-facing test/example for the generated error display behavior? Since the PR description calls out different downstream behavior in Kotlin and Swift, it may be useful to assert one representative error path so we know the exported Display/Debug behavior stays covered.
There was a problem hiding this comment.
That's a great idea. Let me add a few tests right now.
There was a problem hiding this comment.
Thanks for updating this to cover the other error enums too. That addresses my scope question.
3d6a30d to
4d86984
Compare
|
I added 2 tests showcasing how the exceptions behave and look like from the point of view of a Kotlin dev. @reez would you like me to add some for the Swift side as well? In short:
This is, I think, an improvement over what we have currently. My only beef left with it is that at least on the JVM side, your stack traces are now a bit odd, and provide a different type of information than you're used to. I need to see if this is the case for other languages as well. ExampleWith this PR: org.bitcoindevkit.test E ----- begin exception -----
org.bitcoindevkit.test E the word count 13 is not supported
at org.bitcoindevkit.FfiConverterTypeBip39Error.read(bdk.kt:25268)
at org.bitcoindevkit.FfiConverterTypeBip39Error.read(bdk.kt:25263)
...Before, you'd get a different stack trace because the toString method is typically of the following format: org.bitcoindevkit.test E ----- begin exception -----
org.bitcoindevkit.test E org.bitcoindevkit.Bip39Exception$BadWordCount: wordCount=13
at org.bitcoindevkit.FfiConverterTypeBip39Error.read(bdk.kt:25156)
at org.bitcoindevkit.FfiConverterTypeBip39Error.read(bdk.kt:25151) |
318e3f2 to
4bb557c
Compare
Thanks for asking, from my POV I think the Kotlin ones cover this PR since Kotlin’s |
This brings the Display trait we create using the
thiserror::Errormacro to the bindings. We've been implementing the Display trait for all this time, but not passing it on to the bindings!Note that the draft version of this PR implements this just for the
CreateWithPersistErrorenum.See related issues #509 and #964.
Todo
http error with status code 404 and message 'Block not found'instead ofhttp error with status code 404 and message Block not found. Just an idea.In Practice
Here is what this means in practice:
Kotlin
The default toString() method on Exceptions (
className + ": " + message) is overriden by the Display trait. You loose the className when the exception is printed out, but you gain the human-readable message we maintain in the crate. If you want the Exception type, you can still print it. You keep the strongly typed fields (in the example below yourstatusfield is aUShort), and themessagefield is just a stringified concatenation of all the fields. This means you have to know that on BDK exceptions, the human-readable message is not in fact in themessagefield like you expect on typical Kotlin errors, but instead in thetoString()method.Swift
In Swift, two new fields are added to the errors:
descriptionanddebugDescription. Thedescriptionfield now holds the human-readable messages we craft on the structs usingthiserror. The `debugDescription is just the Debug trait on Rust. Note that this is not available in Kotlin, as there is not equivalent "debug" print method or field.Changelog
Checklists
All Submissions:
cargo fmtandcargo clippybefore committingchangelog:*labelNew Features:
Bugfixes: