In this video, I'll talk about the many
faces of Cargo. In other words, I'll give
you a rundown of Cargos functionality.
Cargo is a fantastic tool that comes
with Rust. Cargo is a package manager,
weight a package manager for a viable
systems programming language? Yes finally,
systems programmers can have nice things
too. You can use Cargo to install and
manage packages that you want to use,
Cargo is also the build system, no more
make files, Cargo is also the test Runner,
and the documentation generator, etc.
Cargo is like all the good parts of npm
and pip and bundler and make. Let's go to
the terminal and see Cargo in action to
see the help output for common Cargo sub
commands I can simply type Cargo. The
first command we will use is new, to
create a new Cargo package. By default
Cargo new will create a binary package,
or a package where we'll have an actual
executable that we can run. Let's create
a project called my project.
Cargo has some nice colorful help put
here to let us know what it did, it
created a binary application project
called my project. Let's see what Cargo
created for us.
It created a my project directory with a
Cargo.toml config file, a source
subdirectory with a main.rs source
file. Notice that Cargo uses dot toml
for its config format, that stands for
Tom's obvious minimal language, and it
uses dot RS for Rust source files.
let's take a look at Cargo.toml.
Cargo.toml is the authoritative
config file for our project, it has the
name of our project right here my
project, this determines what the name of
our project is not the name of a
directory, or the name of a Git
repository, it's this setting right here.
We also have the version number Rust
uses semantic versioning, so you will
always see three numbers separated by
dots, and each of the numbers have a
specific meaning. If you're not
acquainted with semantic versioning I
encourage you to go see semver.org for
more information. Then we have the
author's usually it's just a single
author to start with. Cargo does a really
good job of looking for and finding your
name and email address in various places.
One of the places that it looks is your
global Git config, and then we have the
edition so every few years Rust releases
a set of breaking changes as at edition,
by default the edition will be the
latest edition. So right now while in
writing this the latest edition is 2018,
and then you have the dependencies
section where you specify dependencies
that you want Cargo to manage as a
package manager. We will use this a
little bit later on. Now let's go look at
the main dot RS file in the source
subdirectory.
Great we've already got a hello world
program specified for us, so we've got
our function main and then a print line
with hello world, so let's go use Cargo
to run project.
Cargo run compiles and runs your project
in one step,
notice the lines, compiling my project, I
finished it, some information about it,
and then I'm running it. Notice the
location target debug my project,
so when Cargo builds your project it
puts all the build artifacts inside of
the target subdirectory. By default it
builds in debug mode with debug symbols,
so if we look
there's the actual binary. Now we could
run Cargo run again, and you can see that
it checked and saw that nothing had
changed, so it skipped the compiling
stage, and told us hey we're finished and
it ran the project again. Now if you know
that you don't need to recompile, you
could also just run the binary directly.
And then we see just the hello world
output, without the extra Cargo output,
sometimes that's nicer. Now you
definitely want your version control
software to ignore the target
subdirectory. So put that in your dot Git
ignore or the equivalent place if you're
using a version control system other
than Git. Now what if you don't want to
compile in debug mode, we can use the - -
release flag to compile in release mode
instead.
Notice this time target release is the
location of our binary, when you run in
release mode it doesn't have debug
symbols and it's more optimized, it takes
longer to compile but there should be a
noticeable improvement in speed at least
if you have something more substantial
than hello world program. Now let's
explore more features of Cargo by making
a library project. I'm going to use - -
Lib to create a library project.
Let's take a look,
really similar only instead of main dot
RS there is Lib dot RS. Let's take a look
at what Cargo created for us.
On the source subdirectory and Lib dot RS
we can see that it created some tests
for us, but there's no library content
yet. Let's add a function this will be a
public function,
we'll call it four and it will return an
integer,
an integer will simply be for.
So now we have a library with one public
function and a test that ignores it,
let's fix the test.
First we need to import four into the
test module,
next let's go ahead and use it in this
existing test.
So here we assert that the result of
calling our four function is an actual
literal four. So we expect that to
succeed, let's go run it.
Okay, so if we look through this output
we compiled, it finished compelling, and
it's running our tests, and we can see
here our it works
tests passed, so one passing test and
then it runs doc tests, but we don't have
any documentation, let alone tests inside
of our documentation yet.
So it says running zero of those and of
course it passes, and we're done. So we've
run the tests using Cargo and we can see
documentation tests run by default. So
let's go add some documentation, and put
a test in there and see that run. There
are two forms of documentation comments,
you use the first form to document the
enclosing
item, so to document Lib dot RS itself we
need to use this first form, because
there isn't a place outside of Lib de RS
that we can document it. Two slashes and
an exclamation mark is the documentation
comment for the enclosing item,
now we have some nice library
documentation. The next form of
documentation comment adds documentation
to the item that follows it, this is that
form that you will use most often, and
this is just three forward slashes.
Notice that you can use markdown syntax
in your comments, now let's add a test.
[Silence]
Now we can see that my documentation
test actually ran and passed. Of course
documentation is not just for tests, it's
also for the documentation. So let's
generate the documentation and take a
look. The command is Cargo doc, by
default Cargo doc generates
documentation for not only your project
but for all of your dependencies as well.
So I usually add node EPS so it doesn't
generate documentation for all the
dependencies, and then I usually also add
- - open to automatically open the
result in a browser, it looks like this.
Cargo generates really nice
documentation, we can see here is my
crate, here is our top-level
documentation that we created, here's my
list of functions, and here's the
documentation for my function. If we
drill down into the function we can see
the rest of the documentation. I
mentioned that Cargo is a package
manager, let's add a dependency.
Here in the dependency section let's add
Rand as a dependency, so we can generate
random numbers.
Now let's run Cargo build,
Cargo build always builds the entire
dependency chain, even if like here in
our example, we're not actually using our
dependencies, that may change sometime in
the future, but for now be aware that if
you add dependencies that you're not
using you might have a much longer build
time for no reason.
Speaking of build times, Cargo defaults
to parallel builds with the same number
of jobs as CPUs. In the next video, we
will preview the finished project that
we will be creating in this course.