

# Getting started with the SDK for Rust
<a name="getting-started"></a>

Learn how to install, set up, and use the SDK to create a Rust application to access an AWS resource programmatically. 

**Topics**
+ [Authenticating with AWS](credentials.md)
+ [Creating a simple application](hello.md)
+ [Fundamentals](fundamentals.md)

# Authenticating with AWS using AWS SDK for Rust
<a name="credentials"></a>

You must establish how your code authenticates with AWS when developing with AWS services. You can configure programmatic access to AWS resources in different ways depending on the environment and the AWS access available to you. 

To choose your method of authentication and configure it for the SDK, see [Authentication and access](https://docs.aws.amazon.com/sdkref/latest/guide/access.html) in the *AWS SDKs and Tools Reference Guide*. 

We recommend that new users who are developing locally and are not given a method of authentication by their employer should set up AWS IAM Identity Center. This method includes installing the AWS CLI for ease of configuration and for regularly signing in to the AWS access portal. 

 If you choose this method, complete the procedure for [Login for AWS local development using console credentials](https://docs.aws.amazon.com/sdkref/latest/guide/access-login.html) in the *AWS SDKs and Tools Reference Guide*. Afterwards, your environment should contain the following elements:
+ The AWS CLI, which you use to start an AWS access portal session before you run your application.
+ A [shared AWS`config` file](https://docs.aws.amazon.com/sdkref/latest/guide/file-format.html) having a `[default]` profile with a set of configuration values that can be referenced from the SDK. To find the location of this file, see [Location of the shared files](https://docs.aws.amazon.com/sdkref/latest/guide/file-location.html) in the *AWS SDKs and Tools Reference Guide*.
+  The shared `config` file sets the [https://docs.aws.amazon.com/sdkref/latest/guide/feature-region.html](https://docs.aws.amazon.com/sdkref/latest/guide/feature-region.html) setting. This sets the default AWS Region that the SDK uses for AWS requests. This Region is used for SDK service requests that aren't specified with a Region to use. 
+  The SDK uses the profile’s [Login credential provider](https://docs.aws.amazon.com/sdkref/latest/guide/feature-login-credentials.html) configuration to acquire credentials before sending requests to AWS. The `login_session` value, which stores the identity of the management console session that you selected during the login workflow, allows access to the AWS services used in your application. 

  The following sample `config` file shows a default profile set up with Login credentials provider configuration console session selected during the login workflow. The profile's `login_session` setting refers to the named console session selected during the workflow:

  ```
  [default]
  login_session = arn:aws:iam::0123456789012:user/username
  region = us-east-1
  ```
**Note**  
You must enable the `credentials-login` feature of the `aws-config` crate to make use of this credential provider.

## More authentication information
<a name="credother"></a>

Human users, also known as *human identities*, are the people, administrators, developers, operators, and consumers of your applications. They must have an identity to access your AWS environments and applications. Human users that are members of your organization - that means you, the developer - are known as *workforce identities*. 

Use temporary credentials when accessing AWS. You can use an identity provider for your human users to provide federated access to AWS accounts by assuming roles, which provide temporary credentials. For centralized access management, we recommend that you use AWS IAM Identity Center (IAM Identity Center) to manage access to your accounts and permissions within those accounts. For more alternatives, see the following:
+ To learn more about best practices, see [Security best practices in IAM](https://docs.aws.amazon.com/IAM/latest/UserGuide/best-practices.html) in the *IAM User Guide*.
+ To create short-term AWS credentials, see [Temporary Security Credentials](https://docs.aws.amazon.com/IAM/latest/UserGuide/id_credentials_temp.html) in the *IAM User Guide*.
+ To learn about other credential providers supported by SDK for Rust, see [Standardized credential providers](https://docs.aws.amazon.com/sdkref/latest/guide/standardized-credentials.html) in the *AWS SDKs and Tools Reference Guide*.

# Creating a simple application using the AWS SDK for Rust
<a name="hello"></a>

You can get started quickly with AWS SDK for Rust by following this tutorial for creating a simple application that calls an AWS service.

## Prerequisites
<a name="prerequisites"></a>

In order to use the AWS SDK for Rust, you must have Rust and Cargo installed.
+ Install the Rust toolchain: [https://www.rust-lang.org/tools/install](https://www.rust-lang.org/tools/install)
+ Install the `cargo-component` [tool](https://github.com/bytecodealliance/cargo-component) by running command: `cargo install cargo-component`

### Recommended tools:
<a name="recommended-tools"></a>

The following optional tools can be installed in your IDE to assist with code completion and troubleshooting.
+ The rust-analyzer extension, see [Rust in Visual Studio Code](https://code.visualstudio.com/docs/languages/rust).
+ Amazon Q Developer, see [Installing the Amazon Q Developer extension or plugin in your IDE](https://docs.aws.amazon.com/amazonq/latest/qdeveloper-ug/q-in-IDE-setup.html).

## Create your first SDK app
<a name="hello-world"></a>

This procedure creates your first SDK for Rust application that lists your DynamoDB tables.

1. In a terminal or console window, navigate to a location on your computer where you want to create the app.

1. Run the following command to create a `hello_world` directory and populate it with a skeleton Rust project:

   ```
   $ cargo new hello_world --bin
   ```

1. Navigate into the `hello_world` directory and use the following command to add the required dependencies to the app:

   ```
   $ cargo add aws-config aws-sdk-dynamodb tokio --features tokio/full,aws-config/credentials-login
   ```

   These dependencies include the SDK crates that provide configuration features and support for DynamoDB, including the [`tokio` crate](https://crates.io/crates/tokio), which is used to implement asynchronous I/O operations.
**Note**  
Unless you use a feature like `tokio/full` Tokio will not provide an async runtime. The SDK for Rust requires an async runtime.  
The `aws-config/credentials-login` feature enables support for AWS Management Console sign-in credentials, see [Authentication and access in the AWS SDKs and Tools Reference Guide](https://docs.aws.amazon.com/sdkref/latest/guide/access.html) for more information.

1. Update `main.rs` in the `src` directory to contain the following code.

   ```
   use aws_config::meta::region::RegionProviderChain;
   use aws_config::BehaviorVersion;
   use aws_sdk_dynamodb::{Client, Error};
   
   /// Lists your DynamoDB tables in the default Region or us-east-1 if a default Region isn't set.
   #[tokio::main]
   async fn main() -> Result<(), Error> {
       let region_provider = RegionProviderChain::default_provider().or_else("us-east-1");
       let config = aws_config::defaults(BehaviorVersion::latest())
           .region(region_provider)
           .load()
           .await;
       let client = Client::new(&config);
   
       let resp = client.list_tables().send().await?;
   
       println!("Tables:");
   
       let names = resp.table_names();
   
       for name in names {
           println!("  {}", name);
       }
   
       println!();
       println!("Found {} tables", names.len());
   
       Ok(())
   }
   ```
**Note**  
This example only displays the first page of results. See [Using paginated results in the AWS SDK for Rust](paginating.md) to learn how to handle multiple pages of results. 

1. Run the program:

   ```
   $ cargo run
   ```

   You should see a list of your table names.

# Fundamentals for the AWS SDK for Rust
<a name="fundamentals"></a>

Learn fundamentals for programming with the AWS SDK for Rust, such as: Rust programming language fundamentals, information about SDK for Rust crates, project configuration, and SDK for Rust's use of the Tokio runtime.

## Prerequisites
<a name="prerequisites"></a>

In order to use the AWS SDK for Rust, you must have Rust and Cargo installed.
+ Install the Rust toolchain: [https://www.rust-lang.org/tools/install](https://www.rust-lang.org/tools/install)
+ Install the `cargo-component` [tool](https://github.com/bytecodealliance/cargo-component) by running command: `cargo install cargo-component`

### Recommended tools:
<a name="recommended-tools"></a>

The following optional tools can be installed in your IDE to assist with code completion and troubleshooting.
+ The rust-analyzer extension, see [Rust in Visual Studio Code](https://code.visualstudio.com/docs/languages/rust).
+ Amazon Q Developer, see [Installing the Amazon Q Developer extension or plugin in your IDE](https://docs.aws.amazon.com/amazonq/latest/qdeveloper-ug/q-in-IDE-setup.html).

## Rust fundamentals
<a name="rust-fundamentals"></a>

The following are some basics of the Rust programming language that would be helpful to know. All references for more information come from [The Rust Programming Language](https://doc.rust-lang.org/book/title-page.html#the-rust-programming-language).
+ `Cargo.toml` is the standard Rust project configuration file, it contains the dependencies and some metadata about the project. Rust source files have a `.rs` file extension. See [Hello, Cargo\$1](https://doc.rust-lang.org/book/ch01-03-hello-cargo.html).
  + The `Cargo.toml` can be customized with profiles, see [Customizing Builds with Release Profiles](https://doc.rust-lang.org/book/ch14-01-release-profiles.html). These profiles are completely unrelated and independent from AWS's use of profiles within the shared AWS `config` file. 
  + A common way to add library dependencies to your project and this file is to use `cargo add`. See [https://doc.rust-lang.org/cargo/commands/cargo-add.html](https://doc.rust-lang.org/cargo/commands/cargo-add.html).
+ Rust has a basic function structure like the following. The `let` keyword declares a variable and might be paired with assignment (=). If you don't specify a type after `let`, then the compiler will infer one. See [Variables and Mutability](https://doc.rust-lang.org/book/ch03-01-variables-and-mutability.html).

  ```
  fn main() {
      let w = "world";
      println!("Hello {}!", w);
  }
  ```
+ To declare a variable `x` with an explicit type `T`, Rust uses syntax `x: T`. See [Data Types](https://doc.rust-lang.org/book/ch03-02-data-types.html).
+ `struct X {}` defines the new type `X`. Methods are implemented on the custom struct type `X`. Methods for type `X` are declared with implementation blocks prefixed with keyword `impl`. Inside the implementation block, `self` refers to the instance of the struct that the method was called on. See [Keyword `impl`](https://doc.rust-lang.org/std/keyword.impl.html) and [Method Syntax](https://doc.rust-lang.org/book/ch05-03-method-syntax.html).
+ If an exclamation point ("\$1") follows what appears to be a function definition or function call, then the code is defining or calling a macro. See [Macros](https://doc.rust-lang.org/book/ch19-06-macros.html?highlight=macro#macros).
+ In Rust, unrecoverable errors are represented by the `panic!` macro. When a program encounters a `panic!` it will stop running, print a failure message, unwind, clean up the stack, and quit. See [Unrecoverable Errors with `panic!`](https://doc.rust-lang.org/book/ch09-01-unrecoverable-errors-with-panic.html).
+ Rust doesn't support inheritance of functionality from base classes like other programming languages do; `traits` are how Rust provides the overloading of methods. Traits might be thought of as being conceptually similar to an interface. However, traits and true interfaces have differences and are often used differently in the design process. See [Traits: Defining Shared Behavior](https://doc.rust-lang.org/book/ch10-02-traits.html).
  + Polymorphism refers to code that supports functionality for multiple data types without having to individually write each one. Rust supports polymorphism through enums, traits, and generics. See [Inheritance as a Type System and as Code Sharing](https://doc.rust-lang.org/book/ch17-01-what-is-oo.html?#inheritance-as-a-type-system-and-as-code-sharing).
+ Rust is very explicit about memory. Smart pointers "are data structures that act like a pointer but also have additional metadata and capabilities". See [Smart Pointers](https://doc.rust-lang.org/book/ch15-00-smart-pointers.html). 
  + The type `Cow` is a clone-on-write smart pointer that helps transfer memory ownership to the caller when necessary. See [https://doc.rust-lang.org/std/borrow/enum.Cow.html](https://doc.rust-lang.org/std/borrow/enum.Cow.html).
  + The type `Arc` is a Atomically Reference Counted smart pointer that counts allocated instances. See [https://doc.rust-lang.org/std/sync/struct.Arc.html](https://doc.rust-lang.org/std/sync/struct.Arc.html).
+ The SDK for Rust frequently uses the builder pattern for constructing complex types.

## AWS SDK for Rust crate fundamentals
<a name="aws-sdk-crate-fundamentals"></a>
+ The primary core crate for the SDK for Rust functionality is `aws-config`. This is included in the majority of projects because it provides functionality to read configuration from the environment.

  ```
  $ cargo add aws-config
  ```
  + Don't confuse this with the AWS service that is called AWS Config. Since that is a service, it follows the standard convention of AWS service crates and is called `aws-sdk-config`.
+ The SDK for Rust library is separated into different library crates by each AWS service. These crates are available at [https://docs.rs/](https://docs.rs/).
+ AWS service crates follow the naming convention of `aws-sdk-[servicename]`, such as `aws-sdk-s3` and `aws-sdk-dynamodb`.

## Project configuration for working with AWS services
<a name="project-configuration-for-working-with-aws-services"></a>
+ You will need to add a crate to your project for each AWS service that you want your application to use.
+ The recommended way to add a crate is using the command line in your project's directory by running `cargo add [crateName]`, such as `cargo add aws-sdk-s3`.
  + This will add a line to your project's `Cargo.toml` under `[dependencies]`.
  + By default, this will add the latest version of the crate to your project.
+ In your source file, use the `use` statement to bring items from their crates into scope. See [Using External Packages](https://doc.rust-lang.org/book/ch07-04-bringing-paths-into-scope-with-the-use-keyword.html#using-external-packages) on the Rust Programming Language website.
  + Crate names are often hyphenated, but the hyphens get converted to underscores when actually using the crate. For example, the `aws-config` crate is used in code `use` statement as: `use aws_config`.
+ Configuration is a complex topic. Configuration can occur directly in code, or be specified externally in environment variables or config files. For more information, see [Configuring AWS SDK for Rust service clients externally](config-external.md).
  + When the SDK loads your configuration, invalid values are logged instead of halting execution because most settings have reasonable defaults. To learn how to turn on logging, see [Configuring and using logging in the AWS SDK for Rust](logging.md).
  + Most environment variables and config file settings are loaded once when your program starts. Any updates to the values will not be seen until you restart your program.

## Tokio runtime
<a name="tokio-runtime"></a>
+ Tokio is an asynchronous runtime for the SDK for Rust programming language, it executes the `async` tasks. See [tokio.rs](http://tokio.rs/) and [docs.rs/tokio](http://docs.rs/tokio).
+ The SDK for Rust requires an async runtime. We recommend you add the following crate to your projects:

  ```
  $ cargo add tokio --features=full
  ```
+ The `tokio::main` attribute macro creates an async main entry point to your program. To use this macro, add it to the line before your `main` method, as shown in the following:

  ```
  #[tokio::main]
  async fn main() -> Result<(), Error> {
  ```