I was extending a bunch of handlers in my web server tonight, and was stuck with compiler errors that I couldn’t figure out. “Handler trait wasn’t satisfied”… I took a much needed break, poured a glass of wine, and watched some UA-cam. Eventually this video came up and I thought, what the heck, I’m working with Axum. Turns out 53:50 was exactly the solution to my problem. I’m passing in State, Path, and Json into my handlers and the order was wrong. Json was first and it needed to be last. Talk about some divine intervention. Thank you so much for these videos and all you do Jon! They are always a pleasure to watch, even when you aren’t bailing me out.
I took me three sittings to get through all the content. I'm happy you made this recording. I tried to make sense of everything that's documented but it's hard if you're learning rust and only built one or two applications with it. This is a great walk through with much needed hints to get beyond the basic compile errors!
Hey Jon, just wanted to to poke my head in and compliment you on Rust for Rustaceans. I bought it right when I was starting to learn Rust, with an attitude of, "my goal is to get to a point where I more-or-less understand the things in this book." Now, an embarrassing number of months later, I'm reading it and it's beyond awesome. Thanks man and congrats on surviving the move!
"Tower de-crustin' when?" Memes aside - I think this would be the natural progression of the series as you seem to have covered a large portion of the existing Web-Service/Backend crates and associated tooling. Only 1/4 the way through and already had a couple of small things click in the back of my mind so I gotta say - thank you for those moments cos they're so rewarding. Really appreciate these my man, like I cannot express that enough. Need more people like yourself doing good work via 'teardowns' and longer-form videos where in-depth things actually get/can be discussed like this, keep up the awesomeness brother! ♥
OMG, this stream was AWESOME. I am using axum a ton right now but never really dug into it. This really really demystified it for me. Always enjoy your streams even though I often watch them after the fact. I totally understand axum (and Rust stuff in general) way better now. Thank you for your time and awesome work.
Thank you for continuing to share your knowledge. These streams are invaluable to me personally, and I sincerely hope that you stay mentally, physically and financially healthy to keep doing them.
Thank you so much for making these videos. Honestly there are not many Rust videos where they actually break down the code to understand the design and structure to make me a more informed programmer. They seem to be mostly surface level how-to videos.
I just hit the incorrect fromrequest vs from fromrequestparts param order thing with the unhelpful compiler message. Your video helped me understand the reason why it acts that way. SO HELPFUL. Thank you so much for doing these.
Incredible stream / video. Really cleared up a lot of thing about web related concepts as well. Been reading your book and it is equally filled with quality tips and scenarios. Rust was basically my first programming language and the experience was truly (,brutally) humbling. But, the "crust" and "decrust" series was what really made me have those "Ohhhhh, that makes sense now" moments.
This was perfect, exactly what I needed. I was taking my first steps in Rust web dev recently and was trying to look around axum source code to find out how it did the "handler magic", but couldn't quite figure it out. You explained it fantastically.
"Once you have a web server your bottleneck of the application is not dynamic dispatch, so if you can make the ergonomics of using the tool nicer by doing a Box somewhere, it is probably worthwile." Well said 👏
As you were introducing Axum I think it would also be worth including that it does provide ways for creating middlewares and extractors that are a little easier than making a tower service directly.
Really helpful! I think the reason why we can't swap the Json and AppenderHeaders at 1:0815 is that Json doesn't impl IntoResponseParts, since the AppenderHeaders impls IntoResponse so it can be the last param. anyway, it doesn't affect the result.
It's pretty much the same as axum's Handler macro expansion. You can find the implementation in bevy_ecs within exclusive_function_system and exclusive_system_param modules. They use a _all_tuples_ macro as well, which is more generic, as they pass number of variadics to implement for, but is nevertheless the same result.
I was just thinking that it is basically the same as bevy. The stuff that is made possible by all the traits and impls is really awesome and quite magical. But not that magical now, I kind of know how it works.
Imagine my surprise as a Rust noob when -- somehow -- at 48mins into an in-depth video how an HTTP Router works, I hear that at the core of this all we need something called "Cow".
Excellent content. For us Rust beginners, an example of how to write a handler for a custom response type such as a struct of several strings and a Vec[ ] or similar non-standard types would be useful, but perhaps too basic for your typical audience.
If im not mistaken, this looks a lot like the strategy bevy uses to implement its system architecture. Its crazy to me how a technology so complicated and rust type system dependent that its essentially impossible in any systems level language thats not rust is so widespread in the ecosystem. Great explanation. I once combed through source code for hours trying to figure out how the hell bevy knew at compiletime which system params to pass to which functions. Crazy stuff
It's a very interesting pattern, which Bevy also uses and makes it quite easy to work with. Although I have read somewhere that there are some downsides to this pattern, regardless of compile time, but haven't dug deeper into it. It would be nice if variadics were supported at syntax level in Rust. But as I understand it, it's not so easy since Rust would need to add variadic types for generics and functions while keeping its error and debug diagnostics easy to read as well.
please keep on doing these streams. even if its not possible to catch it live. its fantastic to watch as a video :) its always amazing to look at a crate or a topic in rust in more detail. and i think everyone learns a lot from it. As you mentioned tracing would be really intresting to decrust. Or maybe sqlx. espacially the query / query_as macros. I am currtently using actix which would be really intresting to decrust too. But i think with axum you already have covered a great web framework ;).
1:13:00 an alternative to "type erasing" (converting to a Response inside the handler) is to return a `Result`, which is one of the reasons I switched over from Warp (which uses Result for something else so you can't use it for diverging results). The more reliable type-checking is why I personally prefer fully typing most of my axum handlers, rather than using `impl IntoResponse` or `Response`, it's too easy to miss some of the bits you wanted to include then (especially when you use a uniform handler error and Result, in API contexts you probably always want to be sure the error value is the application's error type).
Great video as usual! Thanks, Jon. Now looking forward to the tracing one. Been playing a bit with it, but I am sure your decrusting of the library will make me understand it much more in depth!
It's fascinating to see how you can do all this sort of thing with a strong type system and compile time inference. as opposed to how much of what I see in other languages is based on runtime and reflection trickery
Hi! I love your videos and it is the best advanced video content on rust out there. I will just say that the amount of red errors on the screen really make it hard to ignore and focus on the code, R-A can be too aggressive for my eyes lol
Building medium-large sized type hierarchies, like the one you went through with tower::Service and Handler traits, is a skill I am seriously lacking. Would you have a recommended course of action for me or do you think it's something that comes with experience?
I just discovered your videos. Incredible content. One question: Is there any reason why the authors decided against just following a web standard handler interface? like handlers that take fn(req) -> res? Felt that that would just simplify everything, fit the tower trait, avoid the macro magic and expose the intuition for tower semantics
Hi Jon, thanks for the video! Definitely learned a bunch watching 🙂 I have some trouble wrapping my head around the into_make_service() function. The docs explanation was a bit vague for me, stating MakeService is a Service whose response is another Service. Could you help clarify what this is meant to do?
ah, the type pattern for State is so clever, you can kind of read it as "Still needs to be provided with an S", thus it makes sense that you can only call serve if `S` is `()`. Feels like the inverse of the `ApiBuilder, ApiBuilder` pattern, where instead of denoting what you have it denotes what you need, making it more generic and useful, since you're using actual required types instead of just markers
Could you have a stream for simply implementing an executor? It is hard to figure out what happened behind spawn and how does tokio implement Future. This trait is rarely implemented by normal applications, it just like magical.
In your description it still says "For more details about serde, see ". Seemingly pasted from the serde video, you may want to edit the description. Awesome video btw, this is exactly the content ive been looking for soo long.
@@jonhoo I think I had watched this some years ago when I was even dumber and new to Rust. Now I don't quite remember what it exactly talked about, but I'm not sure it _really_ showed how to implement an Executor 😅
great stream, thank you for sharing. i'm not a big fan of axum's approach to solve this, it is a nice experiment tho. also, i've noticed that alot of the missing time went into searching for implementation, so maybe you could implement it yourself like the hashmap vod. also maybe we can get bigger fonts, been squinting on my phone the whole time xd
Could you have a stream for simply implementing an executor? It is hard to figure out what happened behind spawn and how does tokio implement Future. This trait is rarely implemented by normal applications, it just like magical.
Since I didn't find a better place to vote for new videos, I would like to make this the "please do a decrusting tracing" button 🙌🏻
Yes, this would be amazing.
Yes please!
Wow I didn't know I wanted this, but yes please
+1 for tracing decrusted!
YEP !
Man, you're such a joy to listen to. Thanks for the work you do for us
damn
I was extending a bunch of handlers in my web server tonight, and was stuck with compiler errors that I couldn’t figure out. “Handler trait wasn’t satisfied”… I took a much needed break, poured a glass of wine, and watched some UA-cam. Eventually this video came up and I thought, what the heck, I’m working with Axum.
Turns out 53:50 was exactly the solution to my problem. I’m passing in State, Path, and Json into my handlers and the order was wrong. Json was first and it needed to be last. Talk about some divine intervention. Thank you so much for these videos and all you do Jon! They are always a pleasure to watch, even when you aren’t bailing me out.
I took me three sittings to get through all the content. I'm happy you made this recording. I tried to make sense of everything that's documented but it's hard if you're learning rust and only built one or two applications with it. This is a great walk through with much needed hints to get beyond the basic compile errors!
I love the decrust series. I'm really looking forward to a deep dive into tracing crate!
Hey Jon, just wanted to to poke my head in and compliment you on Rust for Rustaceans. I bought it right when I was starting to learn Rust, with an attitude of, "my goal is to get to a point where I more-or-less understand the things in this book." Now, an embarrassing number of months later, I'm reading it and it's beyond awesome. Thanks man and congrats on surviving the move!
Just bought it :)
These videos are just so great to watch!
"Tower de-crustin' when?"
Memes aside - I think this would be the natural progression of the series as you seem to have covered a large portion of the existing Web-Service/Backend crates and associated tooling.
Only 1/4 the way through and already had a couple of small things click in the back of my mind so I gotta say - thank you for those moments cos they're so rewarding.
Really appreciate these my man, like I cannot express that enough. Need more people like yourself doing good work via 'teardowns' and longer-form videos where in-depth things actually get/can be discussed like this, keep up the awesomeness brother! ♥
OMG, this stream was AWESOME. I am using axum a ton right now but never really dug into it. This really really demystified it for me. Always enjoy your streams even though I often watch them after the fact. I totally understand axum (and Rust stuff in general) way better now. Thank you for your time and awesome work.
If it is possible, don't stop :)
We love you and your videos
You do a great job explaining complex topics. I watched this start-to-finish, which is rare these days. Thank you!
Thank you for continuing to share your knowledge. These streams are invaluable to me personally, and I sincerely hope that you stay mentally, physically and financially healthy to keep doing them.
Thank you so much for making these videos. Honestly there are not many Rust videos where they actually break down the code to understand the design and structure to make me a more informed programmer. They seem to be mostly surface level how-to videos.
I just hit the incorrect fromrequest vs from fromrequestparts param order thing with the unhelpful compiler message. Your video helped me understand the reason why it acts that way. SO HELPFUL. Thank you so much for doing these.
Incredible stream / video. Really cleared up a lot of thing about web related concepts as well. Been reading your book and it is equally filled with quality tips and scenarios. Rust was basically my first programming language and the experience was truly (,brutally) humbling. But, the "crust" and "decrust" series was what really made me have those "Ohhhhh, that makes sense now" moments.
I'd love to see you decrust Bevy :D I use Axum all the time and this was awesome, thanks Jon!
upthumb!
This was perfect, exactly what I needed. I was taking my first steps in Rust web dev recently and was trying to look around axum source code to find out how it did the "handler magic", but couldn't quite figure it out. You explained it fantastically.
"Once you have a web server your bottleneck of the application is not dynamic dispatch, so if you can make the ergonomics of using the tool nicer by doing a Box somewhere, it is probably worthwile."
Well said 👏
Does anyone has a link to "Ralph Youngs introduction to providence" mentionned at 2:04:15 ? Google didn't help me on this
www.ralfj.de/blog/2018/07/24/pointers-and-bytes.html and the two follow up posts he's done :)
As you were introducing Axum I think it would also be worth including that it does provide ways for creating middlewares and extractors that are a little easier than making a tower service directly.
Really helpful! I think the reason why we can't swap the Json and AppenderHeaders at 1:0815 is that Json doesn't impl IntoResponseParts, since the AppenderHeaders impls IntoResponse so it can be the last param. anyway, it doesn't affect the result.
New decrusted from Jon, LET'S GO!
'Decrusting Bevy ECS' next? I really want to know how function is bevy ECS system and it gets it arguments?.
It's pretty much the same as axum's Handler macro expansion. You can find the implementation in bevy_ecs within exclusive_function_system and exclusive_system_param modules.
They use a _all_tuples_ macro as well, which is more generic, as they pass number of variadics to implement for, but is nevertheless the same result.
I was just thinking that it is basically the same as bevy. The stuff that is made possible by all the traits and impls is really awesome and quite magical. But not that magical now, I kind of know how it works.
@@tomaspecl1082 yes it actually make sense to me now. Also know as Extractor functions. It supprised me how simple and powerful this system is.
You're soo good at explaining things! I learned a lot and had fun following your explanations along the way!
Imagine my surprise as a Rust noob when -- somehow -- at 48mins into an in-depth video how an HTTP Router works, I hear that at the core of this all we need something called "Cow".
Excellent content. For us Rust beginners, an example of how to write a handler for a custom response type such as a struct of several strings and a Vec[ ] or similar non-standard types would be useful, but perhaps too basic for your typical audience.
If im not mistaken, this looks a lot like the strategy bevy uses to implement its system architecture. Its crazy to me how a technology so complicated and rust type system dependent that its essentially impossible in any systems level language thats not rust is so widespread in the ecosystem. Great explanation. I once combed through source code for hours trying to figure out how the hell bevy knew at compiletime which system params to pass to which functions. Crazy stuff
Axum is a great crate! This video is awesome! Thank you sir!❤
It's a very interesting pattern, which Bevy also uses and makes it quite easy to work with. Although I have read somewhere that there are some downsides to this pattern, regardless of compile time, but haven't dug deeper into it.
It would be nice if variadics were supported at syntax level in Rust. But as I understand it, it's not so easy since Rust would need to add variadic types for generics and functions while keeping its error and debug diagnostics easy to read as well.
this is a goldmine. Man i wish i was present during the stream, i have so many questions :DD
please keep on doing these streams. even if its not possible to catch it live. its fantastic to watch as a video :) its always amazing to look at a crate or a topic in rust in more detail. and i think everyone learns a lot from it. As you mentioned tracing would be really intresting to decrust. Or maybe sqlx. espacially the query / query_as macros. I am currtently using actix which would be really intresting to decrust too. But i think with axum you already have covered a great web framework ;).
Hey Jon, thanks for soooo much info! Friendly suggestion to set up a telegram group or even channel for new video announcements, topic polls etc
1:13:00 an alternative to "type erasing" (converting to a Response inside the handler) is to return a `Result`, which is one of the reasons I switched over from Warp (which uses Result for something else so you can't use it for diverging results). The more reliable type-checking is why I personally prefer fully typing most of my axum handlers, rather than using `impl IntoResponse` or `Response`, it's too easy to miss some of the bits you wanted to include then (especially when you use a uniform handler error and Result, in API contexts you probably always want to be sure the error value is the application's error type).
You're amazing. I literally needed this right now.
Great video as usual! Thanks, Jon. Now looking forward to the tracing one. Been playing a bit with it, but I am sure your decrusting of the library will make me understand it much more in depth!
Thanks
Every time it is a pleasure to watch
It's fascinating to see how you can do all this sort of thing with a strong type system and compile time inference. as opposed to how much of what I see in other languages is based on runtime and reflection trickery
You display a deep knowledge.
Hi! I love your videos and it is the best advanced video content on rust out there.
I will just say that the amount of red errors on the screen really make it hard to ignore and focus on the code, R-A can be too aggressive for my eyes lol
Is the `==` trait bound syntax documented anywhere? it seems really useful
Building medium-large sized type hierarchies, like the one you went through with tower::Service and Handler traits, is a skill I am seriously lacking. Would you have a recommended course of action for me or do you think it's something that comes with experience?
Please decrust more of the tokio ecosystem!
Axum has "type checking" for tcp/http requests? That's sweet.
1:58:27 What if we used lazy_static?
You're almost typing as fast as you're speaking. I wish I was that fast, but my hands are really holding me back in day to day life XD
such a good stream, thanks man!
I just discovered your videos. Incredible content. One question: Is there any reason why the authors decided against just following a web standard handler interface? like handlers that take fn(req) -> res? Felt that that would just simplify everything, fit the tower trait, avoid the macro magic and expose the intuition for tower semantics
Thanks 😊
Hi Jon, thanks for the video! Definitely learned a bunch watching 🙂
I have some trouble wrapping my head around the into_make_service() function. The docs explanation was a bit vague for me, stating MakeService is a Service whose response is another Service. Could you help clarify what this is meant to do?
ah, the type pattern for State is so clever, you can kind of read it as "Still needs to be provided with an S", thus it makes sense that you can only call serve if `S` is `()`. Feels like the inverse of the `ApiBuilder, ApiBuilder` pattern, where instead of denoting what you have it denotes what you need, making it more generic and useful, since you're using actual required types instead of just markers
Lichess open explorer uses the box leak trick too !
thanks for the video Jon
you got a new subscriber just by the title 😅
Could you have a stream for simply implementing an executor? It is hard to figure out what happened behind spawn and how does tokio implement Future. This trait is rarely implemented by normal applications, it just like magical.
++++++ I been saying this for SO LONG!
Thank you for all your work, your videos are extremely usefull
The moment you started looking for `into_route`, I knew it was going to be ~impossible to explain 😂
Respectfully: you are goated.
hey, i think it would be interesting to decrust the futures crate, because it has useful async types like Stream or Sink
Love you Jon!
Is there anyway we can download these somewhere?
Adding a feature to a crate you're importing is easier if you do cargo add [crate] -F [feature]
I'd love s decrusting Tokio episode
wow, if a handler panics it only panics on that handler task? the web server keeps working. I had no idea. that is so crazy good.
This is gold! 😊😊
Is the vim config public?
just used axum and tera to make a website. was pretty fun.
In your description it still says "For more details about serde, see ". Seemingly pasted from the serde video, you may want to edit the description. Awesome video btw, this is exactly the content ive been looking for soo long.
Oops, good catch, fixed! Thanks 🎉
Awesome thank you
Day N+1 of asking Jon to make a video on creating your own little async/await library/executor.
You mean like ua-cam.com/video/9_3krAQtD2k/v-deo.html :)
@@jonhoo I think I had watched this some years ago when I was even dumber and new to Rust. Now I don't quite remember what it exactly talked about, but I'm not sure it _really_ showed how to implement an Executor 😅
You should do leptos as well :)
+1 for Leptos!
yoo good stuuuff
Please do descripting actix and actix-web
great stream, thank you for sharing.
i'm not a big fan of axum's approach to solve this, it is a nice experiment tho.
also, i've noticed that alot of the missing time went into searching for implementation, so maybe you could implement it yourself like the hashmap vod.
also maybe we can get bigger fonts, been squinting on my phone the whole time xd
Axum and tower have so much confusing types if you're not good at type-fu
Can you decrust tonic?! 😊
Me, a Python developer: "Look what they need to mimic a fraction of *args, **kwargs power".
I like rust, but i hate when i see things like that macro for all tuples. Why cant anything be inferred so you dont need to do dumb things like that
first
thank you. ive discovered axum fairly recently and for me, a young rustacean, it was black box.
Thanks!
Could you have a stream for simply implementing an executor? It is hard to figure out what happened behind spawn and how does tokio implement Future. This trait is rarely implemented by normal applications, it just like magical.
You mean like ua-cam.com/video/9_3krAQtD2k/v-deo.html :)
Oh I mean is to make a "implement" series of videos. I heard that smol had only 1,500 lines of code in the early days.That'll be cool@@jonhoo
Thanks!
Thanks!
Thanks!