For example, let’s start from the code in Listing 7-17 that had multiple restaurant modules. We’ll extract modules into files instead of having all the modules defined in the crate root file. In this case, the crate root file is src/lib.rs, but this procedure also works with binary crates whose crate root file is src/main.rs.
First, we’ll extract the module to its own file. Remove the code inside the curly brackets for the front_of_house
module, leaving only the mod front_of_house;
declaration, so that src/lib.rs contains the code shown in Listing 7-21. Note that this won’t compile until we create the src/front_of_house.rs file in Listing 7-22.
Filename: src/lib.rs
Listing 7-21: Declaring the front_of_house
module whose body will be in src/front_of_house.rs
Next, place the code that was in the curly brackets into a new file named src/front_of_house.rs, as shown in Listing 7-22. The compiler knows to look in this file because it came across the module declaration in the crate root with the name front_of_house
.
Filename: src/front_of_house.rs
Note that you only need to load a file using a mod
declaration once in your module tree. Once the compiler knows the file is part of the project (and knows where in the module tree the code resides because of where you’ve put the mod
statement), other files in your project should refer to the loaded file’s code using a path to where it was declared, as covered in the section. In other words, mod
is not an “include” operation that you may have seen in other programming languages.
Next, we’ll extract the module to its own file. The process is a bit different because hosting
is a child module of front_of_house
, not of the root module. We’ll place the file for hosting
in a new directory that will be named for its ancestors in the module tree, in this case src/front_of_house/.
To start moving hosting
, we change src/front_of_house.rs to contain only the declaration of the hosting
module:
Filename: src/front_of_house.rs
Then we create a src/front_of_house directory and a file hosting.rs to contain the definitions made in the hosting
module:
Filename: src/front_of_house/hosting.rs
We’ve moved each module’s code to a separate file, and the module tree remains the same. The function calls in eat_at_restaurant
will work without any modification, even though the definitions live in different files. This technique lets you move modules to new files as they grow in size.
Note that the pub use crate::front_of_house::hosting
statement in src/lib.rs also hasn’t changed, nor does use
have any impact on what files are compiled as part of the crate. The mod
keyword declares modules, and Rust looks in a file with the same name as the module for the code that goes into that module.
In the next chapter, we’ll look at some collection data structures in the standard library that you can use in your neatly organized code.