Quick Start
Install Rust
If you haven't installed Rust yet, you can install it using the officially provided rustup
.
TIP
The minimum supported Rust version for Salvo is currently 1.85. Run rustup update
to ensure you have a compatible Rust version installed.
Writing Your First Salvo Program
Create a new project:
Add dependencies to Cargo.toml
:
hello/Cargo.toml
[package]
name = "example-hello"
version = "0.1.0"
edition = "2024"
[dependencies]
salvo = { version = "0.77.1" }
tokio = { version = "1", features = ["macros"] }
tracing = "0.1"
tracing-subscriber = "0.3"
In main.rs
, create a simple function handler named hello
. This function simply renders the text "Hello world"
.
hello/src/main.rs
use salvo::prelude::*;
// Handler for English greeting
#[handler]
async fn hello() -> &'static str {
"Hello World"
}
// Handler for Chinese greeting
#[handler]
async fn hello_zh() -> Result<&'static str, ()> {
Ok("你好,世界!")
}
#[tokio::main]
async fn main() {
// Initialize logging subsystem
tracing_subscriber::fmt().init();
// Bind server to port 5800
let acceptor = TcpListener::new("0.0.0.0:5800").bind().await;
// Create router with two endpoints:
// - / (root path) returns English greeting
// - /你好 returns Chinese greeting
let router = Router::new()
.get(hello)
.push(Router::with_path("你好").get(hello_zh));
// Print router structure for debugging
println!("{:?}", router);
// Start serving requests
Server::new(acceptor).serve(router).await;
}
Congratulations, your first Salvo program is complete. Just run cargo run
in your terminal, then open http://127.0.0.1:5800
in your browser.
Detailed Explanation
Here, hello_world
is a Handler
used to process user requests. The #[handler]
macro allows a function to easily implement the Handler
trait. Furthermore, it allows us to abbreviate the function parameters in different ways.
-
Original form:
#[handler]
async fn hello(_req: &mut Request, _depot: &mut Depot, res: &mut Response, _ctrl: &mut FlowCtrl) {
res.render("Hello world");
}
-
You can omit parameters that are not used in the function, like _req
, _depot
, and _ctrl
here, which can be simply left out:
#[handler]
async fn hello(res: &mut Response) {
res.render("Hello world");
}
-
Any type can be used as the return type of the function, as long as it implements the Writer
trait. For example, &str
implements Writer
. When used as a return value, it renders plain text:
#[handler]
async fn hello(res: &mut Response) -> &'static str {
"Hello world"
}
-
More commonly, we need to use Result<T, E>
as the return type to handle errors during function execution. If both T
and E
implement Writer
, then Result<T, E>
can be used as the return value:
#[handler]
async fn hello(res: &mut Response) -> Result<&'static str, ()> {
Ok("Hello world")
}
Awesome HTTP3
HTTP3 is renowned for its speed and efficiency, a feature many developers have eagerly anticipated. Now, Salvo makes it easy to harness the power of HTTP3 and enjoy its benefits!
First, enable the HTTP3 feature in Cargo.toml
, then modify main.rs
like this:
hello-h3/src/main.rs
use salvo::conn::rustls::{Keycert, RustlsConfig};
use salvo::prelude::*;
// Handler function responding with "Hello World" for HTTP/3 requests
#[handler]
async fn hello() -> &'static str {
"Hello World"
}
#[tokio::main]
async fn main() {
// Initialize logging system
tracing_subscriber::fmt().init();
// Load TLS certificate and private key from embedded PEM files
let cert = include_bytes!("../certs/cert.pem").to_vec();
let key = include_bytes!("../certs/key.pem").to_vec();
// Create router with single endpoint
let router = Router::new().get(hello);
// Configure TLS settings using Rustls
let config = RustlsConfig::new(Keycert::new().cert(cert.as_slice()).key(key.as_slice()));
// Create TCP listener with TLS encryption on port 5800
let listener = TcpListener::new(("0.0.0.0", 5800)).rustls(config.clone());
// Create QUIC listener and combine with TCP listener
let acceptor = QuinnListener::new(config.build_quinn_config().unwrap(), ("0.0.0.0", 5800))
.join(listener)
.bind()
.await;
// Start server supporting both HTTP/3 (QUIC) and HTTPS (TCP)
Server::new(acceptor).serve(router).await;
}
Salvo CLI Tool 🛠️
Salvo CLI is a tool designed for the Salvo web framework. It helps create clean, readable code, saving you time for more interesting things in life.
If you have ideas for improving the CLI or find any issues that need fixing, please don't hesitate! Submit an issue; we welcome your insights.
Step 1
Install the CLI tool:
Step 2
Create a new Salvo project using the new
command followed by your project name:
You can quickly start your Salvo project with this simple CLI tool, allowing you to focus on implementing your business logic instead of setting up the project structure. ✨
More Examples
It's recommended to clone the Salvo repository directly and run the examples in the examples
directory. For instance, the following command runs the hello
example:
git clone https://github.com/salvo-rs/salvo
cd salvo/examples
cargo run --bin example-hello
There are many examples in the examples
directory. You can run them using commands like cargo run --bin example-<name>
.