Rust: Encoding and Decoding Base64 Strings using the Windows API
DISCLAIMER
- Windows Only
No Linux/macOS support
DEPENDENCY
In this project, we will use Windows-RS to access Rust APIs.
Traditionally using the following would be enough
However, when using Windows Rust bindings, all interesting things are hidden behind optional features.
The features of interest can be found from the docs for functions that we will use.
As we can see, the features of interest are Security Cryptography and Storage Streams
Imp. Functions
- EncodeToBase64String
Returns Buffer as Output - DecodeFromBase64String
Takes Buffer as input
Buffer to String conversion
- EncodeToBase64String returns IBuffer as output.
- However, in Rust a user would expect to use a String.
- So we need to convert IBuffer to String.
Conversion
- Read Buffer using DataReader
- Allocate a Vector of buffer length size
- Read from the DataReader into the Vector
- Convert the Vector to String
First attempt
As you can see the function is simple and it works.
However, best of Rust users are going to be aware that unwrap while very convenient is not the safest of ways.
One way to solve this easily could be by using from_utf8_unchecked but the function is unsafe
let string = unsafe { String::from_utf8_unchecked(temp) };
Arguably the better and safer way would be to map the FromUTF8 Error to a windows::core::Error
As you can see, we will have to use one of the Windows Error Codes here. To use the error code E_FAIL, we will need to add the feature Win32_Foundation.
Encoding a String to Base64
- Take input as String
- Read String into Buffer
- Call Encode function which returns HSTRING
- Convert HSTRING to String and return
Decoding a Base64 to a String
- Convert String to HSTRING
- Call Decode function which returns IBuffer
- You remember stringify_buffer?
No? Because we use that to convert Buffer to String
Verifying it works
Let’s run a simple unit test to verify
Result
Yeah it works with emojis.
FULL Code
Cross platform base64
There probably are many libraries for his. I found one by the name of base64. It is documented.
My own library
And that is why to simplify it all, I decided to write my own library, win-base64.
I have intentionally written the sample code to be similar to the base64 one.
You can always use this if you decide adding the above solution to your own project is far too verbose.
Dependency management
Contact me!
You can comment here or contact me via LinkedIn.