From a1b2b107e593bc0668e4373db0158788c71c74a4 Mon Sep 17 00:00:00 2001
From: Gerhard de Clercq <11624490+Gerharddc@users.noreply.github.com>
Date: Fri, 7 Feb 2025 10:28:09 +0100
Subject: [PATCH] Add Query Example
This example shows how to extract query string parameters.
---
Cargo.toml | 1 +
examples/query/Cargo.toml | 13 ++++++++
examples/query/src/index.html | 18 ++++++++++
examples/query/src/main.rs | 63 +++++++++++++++++++++++++++++++++++
4 files changed, 95 insertions(+)
create mode 100644 examples/query/Cargo.toml
create mode 100644 examples/query/src/index.html
create mode 100644 examples/query/src/main.rs
diff --git a/Cargo.toml b/Cargo.toml
index a289d1a..bb67f17 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -7,6 +7,7 @@ members = [
"examples/conditional_routing",
"examples/custom_extractor",
"examples/form",
+ "examples/query",
"examples/hello_world",
"examples/hello_world_single_thread",
"examples/huge_requests",
diff --git a/examples/query/Cargo.toml b/examples/query/Cargo.toml
new file mode 100644
index 0000000..407e722
--- /dev/null
+++ b/examples/query/Cargo.toml
@@ -0,0 +1,13 @@
+[package]
+name = "query"
+version = "0.1.0"
+edition = "2021"
+
+# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
+
+[dependencies]
+anyhow = { workspace = true }
+heapless = { workspace = true }
+picoserve = { path = "../../picoserve", features = ["tokio"] }
+serde = { workspace = true }
+tokio = { workspace = true }
diff --git a/examples/query/src/index.html b/examples/query/src/index.html
new file mode 100644
index 0000000..0e3c981
--- /dev/null
+++ b/examples/query/src/index.html
@@ -0,0 +1,18 @@
+
+
+
+
+
+
+ Form Demo
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/examples/query/src/main.rs b/examples/query/src/main.rs
new file mode 100644
index 0000000..5560e28
--- /dev/null
+++ b/examples/query/src/main.rs
@@ -0,0 +1,63 @@
+use std::time::Duration;
+
+use picoserve::routing::{get, get_service};
+
+#[derive(serde::Deserialize)]
+struct QueryParams {
+ a: i32,
+ b: heapless::String<32>,
+}
+
+#[tokio::main(flavor = "current_thread")]
+async fn main() -> anyhow::Result<()> {
+ let port = 8000;
+
+ let app = std::rc::Rc::new(
+ picoserve::Router::new()
+ .route(
+ "/",
+ get_service(picoserve::response::File::html(include_str!("index.html"))),
+ )
+ .route(
+ "/get-thing",
+ get(|picoserve::extract::Query(QueryParams { a, b })| {
+ picoserve::response::DebugValue((("a", a), ("b", b)))
+ }),
+ ),
+ );
+
+ let config = picoserve::Config::new(picoserve::Timeouts {
+ start_read_request: Some(Duration::from_secs(5)),
+ read_request: Some(Duration::from_secs(1)),
+ write: Some(Duration::from_secs(1)),
+ })
+ .keep_connection_alive();
+
+ let socket = tokio::net::TcpListener::bind((std::net::Ipv4Addr::LOCALHOST, port)).await?;
+
+ println!("http://localhost:{port}/");
+
+ tokio::task::LocalSet::new()
+ .run_until(async {
+ loop {
+ let (stream, remote_address) = socket.accept().await?;
+
+ println!("Connection from {remote_address}");
+
+ let app = app.clone();
+ let config = config.clone();
+
+ tokio::task::spawn_local(async move {
+ match picoserve::serve(&app, &config, &mut [0; 2048], stream).await {
+ Ok(handled_requests_count) => {
+ println!(
+ "{handled_requests_count} requests handled from {remote_address}"
+ )
+ }
+ Err(err) => println!("{err:?}"),
+ }
+ });
+ }
+ })
+ .await
+}