mirror of
https://github.com/darkicewolf50/RustBrock.git
synced 2025-06-15 13:04:18 -06:00
started ch 11.1 and finished ch11 prelude
This commit is contained in:
parent
b00b78a773
commit
07fcd28db2
36
Tests.md
Normal file
36
Tests.md
Normal file
@ -0,0 +1,36 @@
|
|||||||
|
# Writing Automated Tests
|
||||||
|
|
||||||
|
"Program testing can be a vary effective way to show the present of bugs, but it is hopelessly inadequate for showing their absence."
|
||||||
|
|
||||||
|
This doesnt mean that we shouldn't try to test as much as we can
|
||||||
|
|
||||||
|
Correctness in our programs is the extent to which our code does what it is intended it to do.
|
||||||
|
|
||||||
|
Rust is desgned with a high dgree of concern about the correctness of programs, correctness is complex and not easy to prove.
|
||||||
|
|
||||||
|
A large part of this compelxity is due to Rust's type system, but the type system cannot catach everything.
|
||||||
|
|
||||||
|
With that being said Rust includes support for writing automated software tests
|
||||||
|
|
||||||
|
For example lets say we wrote a functions `add_two` that adds 2 to whatever number is passed to it.
|
||||||
|
|
||||||
|
This function's signature accepts an integers as a parameter and returns an integer as a result.
|
||||||
|
|
||||||
|
When this is implemented and compiled, Rust will do all of the type checking and borrow checking to enusre that the code is good.
|
||||||
|
|
||||||
|
For instance we cannot pass a `String` value or an invalid reference to this function.
|
||||||
|
|
||||||
|
One thing Rust *can't* check is that this function will do precisely what we inteded it to doe, which is return the parameter plus 2 rather than the paramter plus 10 or minus 50
|
||||||
|
|
||||||
|
This is where tests come in
|
||||||
|
|
||||||
|
We can write tests that assrt, for example in the case where we pass `3` to the `add_two` function, the returned value is `5`.
|
||||||
|
|
||||||
|
We can run these tests whenever we make changes to our code to make sure any existing correct behavior has not changed.
|
||||||
|
|
||||||
|
This chapter will cover:
|
||||||
|
- [How to Write Tests](Writing_Tests.md)
|
||||||
|
- [Controlling How Tests Are Run](How_to_Run.md)
|
||||||
|
- [Test Organization](Test_Organization.md)
|
||||||
|
|
||||||
|
But it will also talk about Rust's testing facilities, the annotations and macros available to you when writing tests, the default behavior and options provided for running your tests and how to organize tests into unit tests and integration tests.
|
108
Writing_Tests.md
Normal file
108
Writing_Tests.md
Normal file
@ -0,0 +1,108 @@
|
|||||||
|
# How to Write Tests
|
||||||
|
|
||||||
|
TAests are Rust functions that verify that non-test code is funcioning as expected
|
||||||
|
|
||||||
|
The bodies of test functions typically perform these three actions:
|
||||||
|
- Set up any needed data or state
|
||||||
|
- Run the code you want to test
|
||||||
|
- Assert that the resutls are what yo expect
|
||||||
|
|
||||||
|
Lets look at the features Rst provides specifically for writing tests that take these actions.
|
||||||
|
|
||||||
|
This incldes the `test` attribute, a few macros, and the `should_panic` attribute
|
||||||
|
|
||||||
|
## The Anatomy of a Test Function
|
||||||
|
|
||||||
|
A test in Rus is a function that is annotated with the `test` attribute.
|
||||||
|
|
||||||
|
Attributes are metadata about peices of Rust code
|
||||||
|
|
||||||
|
An example of this that we used in the past was the `derive` attribute which was used iwth structs in Ch5(Using Structs to Stucture Related Data)
|
||||||
|
|
||||||
|
To change a fucntion into a test function add `#[test]` on the line before `fn`
|
||||||
|
|
||||||
|
When you run your tests with the `cargo test` command
|
||||||
|
|
||||||
|
Rust will then builds a test runner binary that runs the annotated functions and reports whether each test function passes or fails.
|
||||||
|
|
||||||
|
Whenever we make a new library project with Cargo, a test module with a test function with a tet function in it is automaticakky generated for us
|
||||||
|
|
||||||
|
This module give a template for writing your tests.
|
||||||
|
|
||||||
|
This is great becuase you dont have to look up the syntax and structure every time you start a new project.
|
||||||
|
|
||||||
|
You can add as many additional test functions and as many modules as you want using that generated template
|
||||||
|
|
||||||
|
Find an example of this in the library/directory adder
|
||||||
|
|
||||||
|
Lets create the function `add`
|
||||||
|
|
||||||
|
Here is how to create a new library use this command
|
||||||
|
```
|
||||||
|
$ cargo new adder --lib
|
||||||
|
Created library `adder` project
|
||||||
|
$ cd adder
|
||||||
|
```
|
||||||
|
|
||||||
|
Here is what `adder` library should look like/ the generated code
|
||||||
|
```rust
|
||||||
|
pub fn add(left: usize, right: usize) -> usize {
|
||||||
|
left + right
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn it_works() {
|
||||||
|
let result = add(2, 2);
|
||||||
|
assert_eq!(result, 4);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
Lets focus on the `it_works` function.
|
||||||
|
|
||||||
|
Note the `#[test]` annotation; this attribute indicates this is a test function, so that the test runner knows how to treat this function as a test
|
||||||
|
|
||||||
|
We could also have non-test functions in the `tests` module to help set up common scenarios or perform common operations, so we always need a way to indicate which are tests
|
||||||
|
|
||||||
|
This test example uses the `assert_eq!` macro to assert that `result`, which contains the result of adding 2 and 2, equlas 4.
|
||||||
|
|
||||||
|
This servers as an example of the format of a typical test
|
||||||
|
|
||||||
|
After the `cargo test` command runs all tests in our project
|
||||||
|
Here is the result
|
||||||
|
```
|
||||||
|
$ cargo test
|
||||||
|
Compiling adder v0.1.0 (file:///projects/adder)
|
||||||
|
Finished `test` profile [unoptimized + debuginfo] target(s) in 0.57s
|
||||||
|
Running unittests src/lib.rs (target/debug/deps/adder-92948b65e88960b4)
|
||||||
|
|
||||||
|
running 1 test
|
||||||
|
test tests::it_works ... ok
|
||||||
|
|
||||||
|
test result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.00s
|
||||||
|
|
||||||
|
Doc-tests adder
|
||||||
|
|
||||||
|
running 0 tests
|
||||||
|
|
||||||
|
test result: ok. 0 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 0.00s
|
||||||
|
```
|
||||||
|
|
||||||
|
We can see that cargo compiled then ran the test.
|
||||||
|
|
||||||
|
We can see first `running 1 test`, then it shows the function name ``tests::it_works` and then the result of running that test is `ok`
|
||||||
|
|
||||||
|
It then shows the overall summary `test result: ok.` which means that all tests passed, and the portion that reads `1 passed; 0 failed` totals th number of tests that passed or failed
|
||||||
|
|
||||||
|
It's possible to mark a test as ignored so it doesn't run in a particular instance, that will be overed later in this ch
|
||||||
|
|
||||||
|
Because we havent it also shows `0 ignored`
|
||||||
|
|
||||||
|
The `0 measured` statistic is for benchmark tests that measure performance.
|
||||||
|
|
||||||
|
Benchmark tests are only avaialbe in nightly Rust, at the time of 2023 or the writing of the rust programmign language book 2023
|
||||||
|
|
6
adder/Cargo.toml
Normal file
6
adder/Cargo.toml
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
[package]
|
||||||
|
name = "adder"
|
||||||
|
version = "0.1.0"
|
||||||
|
edition = "2021"
|
||||||
|
|
||||||
|
[dependencies]
|
14
adder/src/lib.rs
Normal file
14
adder/src/lib.rs
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
pub fn add(left: u64, right: u64) -> u64 {
|
||||||
|
left + right
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn it_works() {
|
||||||
|
let result = add(2, 2);
|
||||||
|
assert_eq!(result, 4);
|
||||||
|
}
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user