30 Days of Rust - Valley of Despair
Tags: rust, learning, beginners
Published: 2023-05-03 21:03:44

We've made it to double figures folks. And on this momentous day I really ought to remind myself of the Dunning-Kruger effect:
![Dunning-Kruger](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/1mzt4xsctt42lzg8x26c.jpg)

Yesterday I was unknowingly tumbling into the so-called valley of despair. And having gotten even deeper into the valley today, I must admit - I do miss those days of peak stupidity. I was, in fact, so stupid as to believe that a 3 hour YouTube video could teach my all I need to start a full-blown project in Rust. 

You may ask why I've had such a change of heart in 2 days. Well the answer lies in my [feature branch](https://github.com/johnnylarner/time-rs/tree/features/create-subprocess) for my `time-rs` project. This was the painstaking product of tonight's work. I feel like a language learner who wants to tell a funny anecdote but can barely muster a sentence about what I bought in the supermarket today.

Let's list out my open questions for today and summarize what was learned and achieved below.

## Today's open questions
- How do I set up the Rust debugger in VS Code?
- Shoud I focus on reading more Rust code before attempting to do my own project?
- Does it make sense to simply follow a CLI tutorial rather than trying to design my own system (PROBABLY)
- What are `doc` tests?
- Why would a unit test need to return something?
- Can I assign the result of match statement to variable?

## TDD in Rust
I'm a big fan of TDD. Integrating testing into your workflow early helps you spot design issues and bugs not caught by the compiler (because sadly it can't check your if/else statements).  Naturally I began my project by writing the tests first. This lead my to some interesting learnings:
- Store your **unit tests** in the same file as your features
- Dedicate a **tests** folder for integration tests
- Unit tests should be declared as a `mod`, wrapped by a `#[cfg(test)]` decorator
- Each test should have a `#[test]` decorator
- Use any of the assertion macros for testing outputs
- Use the `#[should_panic(msg)]` decorator to test error handling
- Run `cargo test` to run your suite

## To `.expect` or not to `.expect`
One of the first thoughts I had while coding was: how and where do I handle my `Result`? I've seen the `Ok` keyword and the `.expect` method. So which do I pick? Now often consistent code is good, but right now I'm just writing a function so there is `consistency` to work with. 

The Rust docs advise against using `.expect`, but I can see cases where handling a `Result` upstream may just add unnecessary function nesting. As far as I can tell, using `match` is the given way of handling a `Result`. As `match` introduces new scope, you can can't access the variables inside the statement afterwards. But wait: can I assign the result of match statement to a variable like I can in an if/else statement (this isn't rhetorical, it came to me right now!!). 

## Scoping hurts your ego
Python and JavaScript barely care about variable scope. This allows you as the developer to declare this and that and access it in a triple nested if statement in a for loop if you so please. Rust ain't like that. Opening an if/else makes me nervous and unsure about which values I'll be consuming upstream. Right now I've barely even written more than a few functions, but I can see how system design and memory management becomes more challenging once you're managing data at higher and lower levels in your program. Until I get used to this way of thinking, I'm going to have to get used to the pain of scoping.