If you happen to learn rust, it would take no time to realize that macro are something that is worth spending a while. From te macro group, you may not often see include!
being used that much (not surely as println!
of course). But to digest it easy, this macro just reades whatever file path it is given and put the content of that file as rust expression.
# Example
To kick this off with an example, let’s assume we have following two files, namely main.rs
and expr.rs
with given content.
src/main.rs
include!("expr.rs");
fn main () {
println!("Value of external explression is: {}", VALUE);
}
src/expr.rs
const VALUE: u32 = 23;
Now this is pretty odd. There is no VALUE
defined in main.rs and above project compiles just fine. Remember #include
in old school C
and C++
(now you have modules here too)? #include
from C(++)
world would just replace the included header in the specified line, you can think of include!
as being somewhat similar thing.
# Use Cases
Still sometime this macro appears to be helpful, especially in build file to include short external expression at build time. For example, you can let user to execute their own logic while building your crate or binary. And other nice use case is to split your predefined value in seperate file to make you version control diff more pleasing as:
src/main.rs
fn main() {
let active_domains = ["sudipg.com.np", "me.sudipg.com.np", "sudipghimire533.github.io"];
println!("{:#?}", active_domains);
}
Next time you add another active domain you need to directly change the main.rs
file. But instead if we split the active domain list in another file as:
src/main.rs
fn main() {
let active_domains = { include!("active_domains.list") };
}
src/active_domains.list
[
"sudipg.com.np",
"me.sudipg.com.np",
"sudipghimire533.github.io",
"sudipghimire533.gitlab.io",
]
Why that curly {
bracket? Let’s save that for another day. Anyway, Next time when we want to add another domain to the list we simplyt edit domains.list
file and that surely makes the VCS happy ;)
# Pitfalls
Not everything given with are roses. Often times, this macro is not-so-good idea to use within the project that aims to be deterministic. If you mean to make your program file, then simply use use
by splitting program behaviour in modules.
Besides there are some nasty things you should’t have expected. Remember how we only include the files withing same directory as out program file (src). Yeah that was planned. Suppose you wanted to include in other directory being relative to current path i.e you did something like:
include!("includes/program1.rs")
on your shiny mac or linux machine, but when you compile the same program in windows it will fail as paths are seperated by \
in windows as opposed to /
in unix(-like). There you go.
As always thank you for passing by
# Further Reading
- Rust Docs: https://doc.rust-lang.org/std/macro.include.html
- Post tagged rust: https://www.sudipg.com.np/tags/rust/