better logging and http handling

This commit is contained in:
Quentin Gliech
2021-07-30 23:07:29 +02:00
parent 844ada50bb
commit ea5563b0df
5 changed files with 322 additions and 43 deletions

289
Cargo.lock generated
View File

@@ -2,6 +2,12 @@
# It is not intended for manual editing.
version = 3
[[package]]
name = "adler"
version = "1.0.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe"
[[package]]
name = "aead"
version = "0.4.2"
@@ -20,7 +26,7 @@ checksum = "43bb833f0bf979d8475d38fbf09ed3b8a55e1885fe93ad3f93239fc6a4f17b98"
dependencies = [
"getrandom 0.2.3",
"once_cell",
"version_check",
"version_check 0.9.3",
]
[[package]]
@@ -32,6 +38,21 @@ dependencies = [
"memchr",
]
[[package]]
name = "alloc-no-stdlib"
version = "2.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5192ec435945d87bc2f70992b4d818154b5feede43c09fb7592146374eac90a6"
[[package]]
name = "alloc-stdlib"
version = "0.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "697ed7edc0f1711de49ce108c541623a0af97c6c60b2f6e2b65229847ac843c2"
dependencies = [
"alloc-no-stdlib",
]
[[package]]
name = "ansi_term"
version = "0.12.1"
@@ -63,6 +84,20 @@ version = "0.5.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b"
[[package]]
name = "async-compression"
version = "0.3.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5443ccbb270374a2b1055fc72da40e1f237809cd6bb0e97e66d264cd138473a6"
dependencies = [
"brotli",
"flate2",
"futures-core",
"memchr",
"pin-project-lite",
"tokio",
]
[[package]]
name = "async-trait"
version = "0.1.51"
@@ -115,6 +150,15 @@ version = "0.2.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a4521f3e3d031370679b3b140beb36dfe4801b09ac77e30c61941f97df3ef28b"
[[package]]
name = "base64"
version = "0.10.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0b25d992356d2eb0ed82172f5248873db5560c4721f564b13cb5193bda5e668e"
dependencies = [
"byteorder",
]
[[package]]
name = "base64"
version = "0.13.0"
@@ -195,6 +239,27 @@ dependencies = [
"byte-tools",
]
[[package]]
name = "brotli"
version = "3.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7f29919120f08613aadcd4383764e00526fc9f18b6c0895814faeed0dd78613e"
dependencies = [
"alloc-no-stdlib",
"alloc-stdlib",
"brotli-decompressor",
]
[[package]]
name = "brotli-decompressor"
version = "2.3.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1052e1c3b8d4d80eb84a8b94f0a1498797b5fb96314c001156a1c761940ef4ec"
dependencies = [
"alloc-no-stdlib",
"alloc-stdlib",
]
[[package]]
name = "bstr"
version = "0.2.16"
@@ -250,6 +315,12 @@ version = "1.0.69"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e70cc2f62c6ce1868963827bd677764c62d07c3d9a3e1fb1177ee1a9ab199eb2"
[[package]]
name = "cfg-if"
version = "0.1.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822"
[[package]]
name = "cfg-if"
version = "1.0.0"
@@ -262,7 +333,7 @@ version = "0.7.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ea8756167ea0aca10e066cdbe7813bd71d2f24e69b0bc7b50509590cef2ce0b9"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"cipher",
"cpufeatures",
"zeroize",
@@ -359,7 +430,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d5f1c7727e460397e56abc4bddc1d49e07a1ad78fc98eb2e1c8f032a58a2f80d"
dependencies = [
"time 0.2.27",
"version_check",
"version_check 0.9.3",
]
[[package]]
@@ -380,14 +451,32 @@ dependencies = [
"build_const",
]
[[package]]
name = "crc32fast"
version = "1.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "81156fece84ab6a9f2afdb109ce3ae577e42b1228441eded99bd77f627953b1a"
dependencies = [
"cfg-if 1.0.0",
]
[[package]]
name = "crossbeam-channel"
version = "0.3.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c8ec7fcd21571dc78f96cc96243cab8d8f035247c3efd16c687be154c3fa9efa"
dependencies = [
"crossbeam-utils 0.6.6",
]
[[package]]
name = "crossbeam-channel"
version = "0.5.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "06ed27e177f16d65f0f0c22a213e17c696ace5dd64b14258b52f9417ccb52db4"
dependencies = [
"cfg-if",
"crossbeam-utils",
"cfg-if 1.0.0",
"crossbeam-utils 0.8.5",
]
[[package]]
@@ -396,8 +485,18 @@ version = "0.3.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9b10ddc024425c88c2ad148c1b0fd53f4c6d38db9697c9f1588381212fa657c9"
dependencies = [
"cfg-if",
"crossbeam-utils",
"cfg-if 1.0.0",
"crossbeam-utils 0.8.5",
]
[[package]]
name = "crossbeam-utils"
version = "0.6.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "04973fa96e96579258a5091af6003abde64af786b860f18622b82e026cca60e6"
dependencies = [
"cfg-if 0.1.10",
"lazy_static",
]
[[package]]
@@ -406,7 +505,7 @@ version = "0.8.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d82cfc11ce7f2c3faef78d8a684447b40d503d9681acebed6cb728d45940c4db"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"lazy_static",
]
@@ -564,7 +663,19 @@ dependencies = [
"serde_yaml",
"tempfile",
"uncased",
"version_check",
"version_check 0.9.3",
]
[[package]]
name = "flate2"
version = "1.0.20"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "cd3aec53de10fe96d7d8c565eb17f2c687bb5518a2ec453b5b1252964526abe0"
dependencies = [
"cfg-if 1.0.0",
"crc32fast",
"libc",
"miniz_oxide",
]
[[package]]
@@ -699,7 +810,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "501466ecc8a30d1d3b7fc9229b122b2ce8ed6e9d9223f1138d4babb253e51817"
dependencies = [
"typenum",
"version_check",
"version_check 0.9.3",
]
[[package]]
@@ -708,7 +819,7 @@ version = "0.1.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8fc3cb4d91f53b50155bdcfd23f6a4c39ae1969c2ae85982b135750cccaf5fce"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"libc",
"wasi 0.9.0+wasi-snapshot-preview1",
]
@@ -719,7 +830,7 @@ version = "0.2.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7fcd999463524c52659517fe2cea98493cfe485d10565e7b0fb07dbba7ad2753"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"libc",
"wasi 0.10.0+wasi-snapshot-preview1",
]
@@ -785,13 +896,27 @@ dependencies = [
"hashbrown",
]
[[package]]
name = "hdrhistogram"
version = "6.3.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "08d331ebcdbca4acbefe5da8c3299b2e246f198a8294cc5163354e743398b89d"
dependencies = [
"base64 0.10.1",
"byteorder",
"crossbeam-channel 0.3.9",
"flate2",
"nom 4.2.3",
"num-traits",
]
[[package]]
name = "headers"
version = "0.3.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f0b7591fb62902706ae8e7aaff416b1b0fa2c0fd0878b46dc13baa3712d8a855"
dependencies = [
"base64",
"base64 0.13.0",
"bitflags",
"bytes",
"headers-core",
@@ -931,7 +1056,7 @@ version = "0.4.18"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "713f1b139373f96a2e0ce3ac931cd01ee973c3c5dd7c40c0c2efe96ad2b6751d"
dependencies = [
"crossbeam-utils",
"crossbeam-utils 0.8.5",
"globset",
"lazy_static",
"log",
@@ -983,7 +1108,16 @@ version = "0.1.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bee0328b1209d157ef001c94dd85b4f8f64139adb0eac2659f4b08382b2f474d"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
]
[[package]]
name = "iri-string"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8326cf970601ca3f0a79e1727b606009d75a8104a0489d146982828141b2c044"
dependencies = [
"nom 6.1.2",
]
[[package]]
@@ -1024,7 +1158,7 @@ checksum = "6607c62aa161d23d17a9072cc5da0be67cdfc89d3afb1e8d9c842bebc2525ffe"
dependencies = [
"arrayvec",
"bitflags",
"cfg-if",
"cfg-if 1.0.0",
"ryu",
"static_assertions",
]
@@ -1056,7 +1190,7 @@ version = "0.4.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "51b9bbe6c47d51fc3e1a9b945965946b4c44142ab8792c50835a980d362c2710"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
]
[[package]]
@@ -1095,6 +1229,7 @@ dependencies = [
"data-encoding",
"figment",
"headers",
"hyper",
"mime",
"oauth2-types",
"password-hash",
@@ -1107,6 +1242,8 @@ dependencies = [
"tera",
"thiserror",
"tokio",
"tower",
"tower-http",
"tracing",
"tracing-subscriber",
"url",
@@ -1146,6 +1283,16 @@ dependencies = [
"unicase",
]
[[package]]
name = "miniz_oxide"
version = "0.4.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a92518e98c078586bc6c934028adcca4c92a53d6a958196de835170a01d84e4b"
dependencies = [
"adler",
"autocfg",
]
[[package]]
name = "mio"
version = "0.7.13"
@@ -1186,6 +1333,16 @@ dependencies = [
"twoway",
]
[[package]]
name = "nom"
version = "4.2.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2ad2a91a8e869eeb30b9cb3119ae87773a8f4ae617f41b1eb9c154b2905f7bd6"
dependencies = [
"memchr",
"version_check 0.1.5",
]
[[package]]
name = "nom"
version = "6.1.2"
@@ -1196,7 +1353,7 @@ dependencies = [
"funty",
"lexical-core",
"memchr",
"version_check",
"version_check 0.9.3",
]
[[package]]
@@ -1292,7 +1449,7 @@ version = "0.8.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fa7a782938e745763fe6907fc6ba86946d72f49fe7e21de074e08128a99fb018"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"instant",
"libc",
"redox_syscall",
@@ -1477,7 +1634,7 @@ dependencies = [
"proc-macro2",
"quote",
"syn",
"version_check",
"version_check 0.9.3",
]
[[package]]
@@ -1488,7 +1645,7 @@ checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869"
dependencies = [
"proc-macro2",
"quote",
"version_check",
"version_check 0.9.3",
]
[[package]]
@@ -1521,7 +1678,7 @@ dependencies = [
"proc-macro2",
"quote",
"syn",
"version_check",
"version_check 0.9.3",
"yansi",
]
@@ -1711,7 +1868,7 @@ version = "0.19.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "35edb675feee39aec9c99fa5ff985081995a06d594114ae14cbe797ad7b7a6d7"
dependencies = [
"base64",
"base64 0.13.0",
"log",
"ring",
"sct",
@@ -1918,7 +2075,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1a0c8611594e2ab4ebbf06ec7cbbf0a99450b8570e96cbf5188b5d5f6ef18d81"
dependencies = [
"block-buffer 0.9.0",
"cfg-if",
"cfg-if 1.0.0",
"cpufeatures",
"digest 0.9.0",
"opaque-debug 0.3.0",
@@ -1937,7 +2094,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b362ae5752fd2137731f9fa25fd4d9058af34666ca1966fb969119cc35719f12"
dependencies = [
"block-buffer 0.9.0",
"cfg-if",
"cfg-if 1.0.0",
"cpufeatures",
"digest 0.9.0",
"opaque-debug 0.3.0",
@@ -2006,7 +2163,7 @@ checksum = "6d86e3c77ff882a828346ba401a7ef4b8e440df804491c6064fe8295765de71c"
dependencies = [
"lazy_static",
"maplit",
"nom",
"nom 6.1.2",
"regex",
"unicode_categories",
]
@@ -2029,15 +2186,15 @@ checksum = "7f23af36748ec8ea8d49ef8499839907be41b0b1178a4e82b8cb45d29f531dc9"
dependencies = [
"ahash",
"atoi",
"base64",
"base64 0.13.0",
"bitflags",
"byteorder",
"bytes",
"chrono",
"crc",
"crossbeam-channel",
"crossbeam-channel 0.5.1",
"crossbeam-queue",
"crossbeam-utils",
"crossbeam-utils 0.8.5",
"dirs",
"either",
"futures-channel",
@@ -2109,7 +2266,7 @@ version = "0.2.17"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e113fb6f3de07a243d434a56ec6f186dfd51cb08448239fe7bcae73f87ff28ff"
dependencies = [
"version_check",
"version_check 0.9.3",
]
[[package]]
@@ -2235,7 +2392,7 @@ version = "3.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dac1c663cfc93810f88aed9b8941d48cabf856a1b111c29a40439018d870eb22"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"libc",
"rand 0.8.4",
"redox_syscall",
@@ -2334,7 +2491,7 @@ dependencies = [
"standback",
"stdweb",
"time-macros",
"version_check",
"version_check 0.9.3",
"winapi",
]
@@ -2456,6 +2613,58 @@ dependencies = [
"tokio",
]
[[package]]
name = "tower"
version = "0.4.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f60422bc7fefa2f3ec70359b8ff1caff59d785877eb70595904605bcc412470f"
dependencies = [
"futures-core",
"futures-util",
"hdrhistogram",
"indexmap",
"pin-project",
"rand 0.8.4",
"slab",
"tokio",
"tokio-stream",
"tokio-util",
"tower-layer",
"tower-service",
"tracing",
]
[[package]]
name = "tower-http"
version = "0.1.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0b7b56efe69aa0ad2b5da6b942e57ea9f6fe683b7a314d4ff48662e2c8838de1"
dependencies = [
"async-compression",
"base64 0.13.0",
"bytes",
"futures-core",
"futures-util",
"http",
"http-body",
"iri-string",
"mime",
"mime_guess",
"pin-project",
"tokio",
"tokio-util",
"tower",
"tower-layer",
"tower-service",
"tracing",
]
[[package]]
name = "tower-layer"
version = "0.3.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "343bc9466d3fe6b0f960ef45960509f84480bf4fd96f92901afe7ff3df9d3a62"
[[package]]
name = "tower-service"
version = "0.3.1"
@@ -2468,7 +2677,7 @@ version = "0.1.26"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "09adeb8c97449311ccd28a427f96fb563e7fd31aabf994189879d9da2394b89d"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"log",
"pin-project-lite",
"tracing-attributes",
@@ -2550,7 +2759,7 @@ version = "0.12.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8ada8297e8d70872fa9a551d93250a9f407beb9f37ef86494eb20012a2ff7c24"
dependencies = [
"base64",
"base64 0.13.0",
"byteorder",
"bytes",
"http",
@@ -2590,7 +2799,7 @@ version = "0.9.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5baeed7327e25054889b9bd4f975f32e5f4c5d434042d59ab6cd4142c0a76ed0"
dependencies = [
"version_check",
"version_check 0.9.3",
]
[[package]]
@@ -2649,7 +2858,7 @@ version = "2.6.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "50f37be617794602aabbeee0be4f259dc1778fabe05e2d67ee8f79326d5cb4f6"
dependencies = [
"version_check",
"version_check 0.9.3",
]
[[package]]
@@ -2741,6 +2950,12 @@ version = "0.8.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f1bddf1187be692e79c5ffeab891132dfb0f236ed36a43c7ed39f1165ee20191"
[[package]]
name = "version_check"
version = "0.1.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "914b1a6776c4c929a602fafd8bc742e06365d4bcbe48c30f9cca5824f70dc9dd"
[[package]]
name = "version_check"
version = "0.9.3"
@@ -2815,7 +3030,7 @@ version = "0.2.74"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d54ee1d4ed486f78874278e63e4069fc1ab9f6a18ca492076ffb90c5eb2997fd"
dependencies = [
"cfg-if",
"cfg-if 1.0.0",
"wasm-bindgen-macro",
]

View File

@@ -8,7 +8,7 @@ license = "Apache-2.0"
[dependencies]
# Async runtime
tokio = { version = "1.9.0", features = ["full"] }
async-trait = "0.1.50"
async-trait = "0.1.51"
# Logging and tracing
tracing = "0.1.26"
@@ -20,6 +20,11 @@ anyhow = "1.0.42"
# Web server
warp = "0.3.1"
tower = { version = "0.4.8", features = ["full"] }
tower-http = { version = "0.1.1", features = ["full"] }
hyper = { version = "0.14.11", features = ["full"] }
# Template engine
tera = "1.12.1"
# Database access

View File

@@ -12,10 +12,21 @@
// See the License for the specific language governing permissions and
// limitations under the License.
use std::net::SocketAddr;
use std::{
net::{SocketAddr, TcpListener},
time::Duration,
};
use anyhow::Context;
use clap::Clap;
use hyper::{header, Server};
use tower::{make::Shared, ServiceBuilder};
use tower_http::{
compression::CompressionLayer,
sensitive_headers::SetSensitiveHeadersLayer,
trace::{DefaultMakeSpan, DefaultOnResponse, TraceLayer},
LatencyUnit,
};
use super::RootCommand;
use crate::{config::RootConfig, templates::Templates};
@@ -27,6 +38,9 @@ impl ServerCommand {
pub async fn run(&self, root: &RootCommand) -> anyhow::Result<()> {
let config: RootConfig = root.load_config()?;
let addr: SocketAddr = config.http.address.parse()?;
let listener = TcpListener::bind(addr)?;
// Connect to the database
let pool = config.database.connect().await?;
@@ -34,9 +48,37 @@ impl ServerCommand {
let templates = Templates::load().context("could not load templates")?;
// Start the server
let address: SocketAddr = config.http.address.parse()?;
let root = crate::handlers::root(&pool, &templates, &config);
warp::serve(root).run(address).await;
let warp_service = warp::service(root);
let service = ServiceBuilder::new()
// Add high level tracing/logging to all requests
.layer(
TraceLayer::new_for_http()
.make_span_with(DefaultMakeSpan::new().include_headers(true))
.on_response(
DefaultOnResponse::new()
.include_headers(true)
.latency_unit(LatencyUnit::Micros),
),
)
// Set a timeout
.timeout(Duration::from_secs(10))
// Compress responses
.layer(CompressionLayer::new())
// Mark the `Authorization` and `Cookie` headers as sensitive so it doesn't show in logs
.layer(SetSensitiveHeadersLayer::new(vec![
header::AUTHORIZATION,
header::COOKIE,
]))
.service(warp_service);
tracing::info!("Listening on http://{}", listener.local_addr().unwrap());
Server::from_tcp(listener)?
.serve(Shared::new(service))
.await?;
Ok(())
}

View File

@@ -18,7 +18,11 @@ use anyhow::Context;
use schemars::{gen::SchemaGenerator, schema::Schema, JsonSchema};
use serde::{Deserialize, Serialize};
use serde_with::{serde_as, skip_serializing_none};
use sqlx::postgres::{PgPool, PgPoolOptions};
use sqlx::{
postgres::{PgConnectOptions, PgPool, PgPoolOptions},
ConnectOptions,
};
use tracing::log::LevelFilter;
use super::ConfigurationSection;
@@ -97,13 +101,23 @@ pub struct DatabaseConfig {
impl DatabaseConfig {
#[tracing::instrument(err)]
pub async fn connect(&self) -> anyhow::Result<PgPool> {
let mut options = self
.uri
.parse::<PgConnectOptions>()
.context("invalid database URL")?
.application_name("matrix-authentication-service");
options
.log_statements(LevelFilter::Debug)
.log_slow_statements(LevelFilter::Warn, Duration::from_millis(100));
PgPoolOptions::new()
.max_connections(self.max_connections)
.min_connections(self.min_connections)
.connect_timeout(self.connect_timeout)
.idle_timeout(self.idle_timeout)
.max_lifetime(self.max_lifetime)
.connect(&self.uri)
.connect_with(options)
.await
.context("could not connect to the database")
}

View File

@@ -12,6 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
use hyper::StatusCode;
use sqlx::PgPool;
use warp::{filters::BoxedFilter, Filter};
@@ -31,5 +32,7 @@ pub fn root(
health(pool)
.or(oauth2(&config.oauth2))
.or(views(pool, templates, &config.csrf, &config.cookies))
.or(warp::get().map(|| StatusCode::NOT_FOUND))
.with(warp::log(module_path!()))
.boxed()
}