aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlex Auvolat <alex@adnab.me>2021-12-07 15:20:45 +0100
committerAlex Auvolat <alex@adnab.me>2021-12-07 15:20:45 +0100
commitcd7e5ad034b75d659d4d87a752ab7b11cf75de12 (patch)
tree32773f9758b33188402e137d435bdd61ce01b280
parent5535c4951a832d65755afa53822a36e96681320f (diff)
downloadtricot-cd7e5ad034b75d659d4d87a752ab7b11cf75de12.tar.gz
tricot-cd7e5ad034b75d659d4d87a752ab7b11cf75de12.zip
Got a reverse proxy
-rw-r--r--Cargo.lock642
-rw-r--r--Cargo.toml8
-rw-r--r--src/cert.rs6
-rw-r--r--src/cert_store.rs23
-rw-r--r--src/https.rs126
-rw-r--r--src/main.rs8
-rw-r--r--src/reverse_proxy.rs114
7 files changed, 863 insertions, 64 deletions
diff --git a/Cargo.lock b/Cargo.lock
index cd91d8b..5c7e156 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -42,7 +42,7 @@ checksum = "d9b39be18770d11421cdb1b9947a45dd3f37e93092cbf377614828a319d5fee8"
dependencies = [
"hermit-abi",
"libc",
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -76,6 +76,23 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8f1e260c3a9040a7c19a12468758f4c16f31a81a1fe087482be9570ec864bb6c"
[[package]]
+name = "byteorder"
+version = "1.4.3"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "14c189c53d098945499cdfa7ecc63567cf3886b3332b312a5b4585d8d3a6a610"
+
+[[package]]
+name = "bytes"
+version = "0.4.12"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "206fdffcfa2df7cbe15601ef46c813fce0965eb3286db6b56c583b814b51c81c"
+dependencies = [
+ "byteorder",
+ "either",
+ "iovec",
+]
+
+[[package]]
name = "bytes"
version = "1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -89,6 +106,12 @@ checksum = "22a9137b95ea06864e018375b72adfb7db6e6f68cfc8df5a04d00288050485ee"
[[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"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
@@ -104,7 +127,7 @@ dependencies = [
"num-traits",
"serde",
"time 0.1.43",
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -114,6 +137,15 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fff857943da45f546682664a79488be82e69e43c1a7a2307679ab9afb3a66d2e"
[[package]]
+name = "cloudabi"
+version = "0.0.3"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "ddfc5b9aa5d4507acaf872de71051dfd0e309860e88966e1051e462a077aac4f"
+dependencies = [
+ "bitflags",
+]
+
+[[package]]
name = "const_fn"
version = "0.4.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -163,18 +195,72 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5827cebf4670468b8772dd191856768aedcb1b0278a04f989f7766351917b9dc"
[[package]]
+name = "crossbeam-deque"
+version = "0.7.4"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "c20ff29ded3204c5106278a81a38f4b482636ed4fa1e6cfbeef193291beb29ed"
+dependencies = [
+ "crossbeam-epoch",
+ "crossbeam-utils",
+ "maybe-uninit",
+]
+
+[[package]]
+name = "crossbeam-epoch"
+version = "0.8.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "058ed274caafc1f60c4997b5fc07bf7dc7cca454af7c6e81edffe5f33f70dace"
+dependencies = [
+ "autocfg",
+ "cfg-if 0.1.10",
+ "crossbeam-utils",
+ "lazy_static",
+ "maybe-uninit",
+ "memoffset",
+ "scopeguard",
+]
+
+[[package]]
+name = "crossbeam-queue"
+version = "0.2.3"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "774ba60a54c213d409d5353bda12d49cd68d14e45036a285234c8d6f91f92570"
+dependencies = [
+ "cfg-if 0.1.10",
+ "crossbeam-utils",
+ "maybe-uninit",
+]
+
+[[package]]
+name = "crossbeam-utils"
+version = "0.7.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "c3c7c73a2d1e9fc0886a08b93e98eb643461230d5f1925e4036204d5f2e261a8"
+dependencies = [
+ "autocfg",
+ "cfg-if 0.1.10",
+ "lazy_static",
+]
+
+[[package]]
name = "discard"
version = "1.0.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "212d0f5754cb6769937f4501cc0e67f4f4483c8d2c3e1e922ee9edbe4ab4c7c0"
[[package]]
+name = "either"
+version = "1.6.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "e78d4f1cc4ae33bbfc157ed5d5a5ef3bc29227303d595861deb238fcec4e9457"
+
+[[package]]
name = "encoding_rs"
version = "0.8.29"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a74ea89a0a1b98f6332de42c95baff457ada66d1cb4030f9ff151b2041a1c746"
dependencies = [
- "cfg-if",
+ "cfg-if 1.0.0",
]
[[package]]
@@ -231,6 +317,28 @@ dependencies = [
]
[[package]]
+name = "fuchsia-zircon"
+version = "0.3.3"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82"
+dependencies = [
+ "bitflags",
+ "fuchsia-zircon-sys",
+]
+
+[[package]]
+name = "fuchsia-zircon-sys"
+version = "0.3.3"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7"
+
+[[package]]
+name = "futures"
+version = "0.1.31"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "3a471a38ef8ed83cd6e40aa59c1ffe17db6855c18e3604d9c4ed8c08ebc28678"
+
+[[package]]
name = "futures"
version = "0.3.18"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -262,6 +370,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "629316e42fe7c2a0b9a65b47d159ceaa5453ab14e8f0a3c5eedbb8cd55b4a445"
[[package]]
+name = "futures-cpupool"
+version = "0.1.8"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "ab90cde24b3319636588d0c35fe03b1333857621051837ed769faefb4c2162e4"
+dependencies = [
+ "futures 0.1.31",
+ "num_cpus",
+]
+
+[[package]]
name = "futures-executor"
version = "0.3.18"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -325,26 +443,44 @@ 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",
]
[[package]]
name = "h2"
+version = "0.1.26"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "a5b34c246847f938a410a03c5458c7fee2274436675e76d8b903c08efc29c462"
+dependencies = [
+ "byteorder",
+ "bytes 0.4.12",
+ "fnv",
+ "futures 0.1.31",
+ "http 0.1.21",
+ "indexmap",
+ "log",
+ "slab",
+ "string",
+ "tokio-io",
+]
+
+[[package]]
+name = "h2"
version = "0.3.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7fd819562fcebdac5afc5c113c3ec36f902840b70fd4fc458799c8ce4607ae55"
dependencies = [
- "bytes",
+ "bytes 1.1.0",
"fnv",
"futures-core",
"futures-sink",
"futures-util",
- "http",
+ "http 0.2.5",
"indexmap",
"slab",
- "tokio",
+ "tokio 1.14.0",
"tokio-util",
"tracing",
]
@@ -366,23 +502,46 @@ dependencies = [
[[package]]
name = "http"
+version = "0.1.21"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "d6ccf5ede3a895d8856620237b2f02972c1bbc78d2965ad7fe8838d4a0ed41f0"
+dependencies = [
+ "bytes 0.4.12",
+ "fnv",
+ "itoa",
+]
+
+[[package]]
+name = "http"
version = "0.2.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1323096b05d41827dadeaee54c9981958c0f94e670bc94ed80037d1a7b8b186b"
dependencies = [
- "bytes",
+ "bytes 1.1.0",
"fnv",
"itoa",
]
[[package]]
name = "http-body"
+version = "0.1.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "6741c859c1b2463a423a1dbce98d418e6c3c3fc720fb0d45528657320920292d"
+dependencies = [
+ "bytes 0.4.12",
+ "futures 0.1.31",
+ "http 0.1.21",
+ "tokio-buf",
+]
+
+[[package]]
+name = "http-body"
version = "0.4.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1ff4f84919677303da5f147645dbea6b1881f368d03ac84e1dc09031ebd7b2c6"
dependencies = [
- "bytes",
- "http",
+ "bytes 1.1.0",
+ "http 0.2.5",
"pin-project-lite",
]
@@ -409,26 +568,68 @@ dependencies = [
[[package]]
name = "hyper"
+version = "0.12.36"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "5c843caf6296fc1f93444735205af9ed4e109a539005abb2564ae1d6fad34c52"
+dependencies = [
+ "bytes 0.4.12",
+ "futures 0.1.31",
+ "futures-cpupool",
+ "h2 0.1.26",
+ "http 0.1.21",
+ "http-body 0.1.0",
+ "httparse",
+ "iovec",
+ "itoa",
+ "log",
+ "net2",
+ "rustc_version",
+ "time 0.1.43",
+ "tokio 0.1.22",
+ "tokio-buf",
+ "tokio-executor",
+ "tokio-io",
+ "tokio-reactor",
+ "tokio-tcp",
+ "tokio-threadpool",
+ "tokio-timer",
+ "want 0.2.0",
+]
+
+[[package]]
+name = "hyper"
version = "0.14.15"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "436ec0091e4f20e655156a30a0df3770fe2900aa301e548e08446ec794b6953c"
dependencies = [
- "bytes",
+ "bytes 1.1.0",
"futures-channel",
"futures-core",
"futures-util",
- "h2",
- "http",
- "http-body",
+ "h2 0.3.7",
+ "http 0.2.5",
+ "http-body 0.4.4",
"httparse",
"httpdate",
"itoa",
"pin-project-lite",
"socket2",
- "tokio",
+ "tokio 1.14.0",
"tower-service",
"tracing",
- "want",
+ "want 0.3.0",
+]
+
+[[package]]
+name = "hyper-reverse-proxy"
+version = "0.4.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "474f19c624c13005d914fc4a73aa2a2921b0371f5f7b748146f5130685492ce8"
+dependencies = [
+ "futures 0.1.31",
+ "hyper 0.12.36",
+ "lazy_static",
+ "unicase",
]
[[package]]
@@ -437,10 +638,10 @@ version = "0.5.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d6183ddfa99b85da61a140bea0efc93fdf56ceaa041b37d553518030827f9905"
dependencies = [
- "bytes",
- "hyper",
+ "bytes 1.1.0",
+ "hyper 0.14.15",
"native-tls",
- "tokio",
+ "tokio 1.14.0",
"tokio-native-tls",
]
@@ -466,6 +667,15 @@ dependencies = [
]
[[package]]
+name = "iovec"
+version = "0.1.4"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "b2b3ea6ff95e175473f8ffe6a7eb7c00d054240321b84c57051175fe3c1e075e"
+dependencies = [
+ "libc",
+]
+
+[[package]]
name = "ipnet"
version = "2.3.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -487,6 +697,16 @@ dependencies = [
]
[[package]]
+name = "kernel32-sys"
+version = "0.2.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d"
+dependencies = [
+ "winapi 0.2.8",
+ "winapi-build",
+]
+
+[[package]]
name = "lazy_static"
version = "1.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -499,12 +719,21 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f98a04dce437184842841303488f70d0188c5f51437d2a834dc097eafa909a01"
[[package]]
+name = "lock_api"
+version = "0.3.4"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "c4da24a77a3d8a6d4862d95f72e6fdb9c09a643ecdb402d754004a557f2bec75"
+dependencies = [
+ "scopeguard",
+]
+
+[[package]]
name = "log"
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]]
@@ -514,12 +743,27 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a3e378b66a060d48947b590737b30a1be76706c8dd7b8ba0f2fe3989c68a853f"
[[package]]
+name = "maybe-uninit"
+version = "2.0.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "60302e4db3a61da70c0cb7991976248362f30319e88850c487b9b95bbf059e00"
+
+[[package]]
name = "memchr"
version = "2.4.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "308cc39be01b73d0d18f82a0e7b2a3df85245f84af96fdddc5d202d27e47b86a"
[[package]]
+name = "memoffset"
+version = "0.5.6"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "043175f069eda7b85febe4a74abbaeff828d9f8b448515d3151a14a3542811aa"
+dependencies = [
+ "autocfg",
+]
+
+[[package]]
name = "mime"
version = "0.3.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -527,15 +771,46 @@ checksum = "2a60c7ce501c71e03a9c9c0d35b861413ae925bd979cc7a4e30d060069aaac8d"
[[package]]
name = "mio"
+version = "0.6.23"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "4afd66f5b91bf2a3bc13fad0e21caedac168ca4c707504e75585648ae80e4cc4"
+dependencies = [
+ "cfg-if 0.1.10",
+ "fuchsia-zircon",
+ "fuchsia-zircon-sys",
+ "iovec",
+ "kernel32-sys",
+ "libc",
+ "log",
+ "miow 0.2.2",
+ "net2",
+ "slab",
+ "winapi 0.2.8",
+]
+
+[[package]]
+name = "mio"
version = "0.7.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8067b404fe97c70829f082dec8bcf4f71225d7eaea1d8645349cb76fa06205cc"
dependencies = [
"libc",
"log",
- "miow",
+ "miow 0.3.7",
"ntapi",
- "winapi",
+ "winapi 0.3.9",
+]
+
+[[package]]
+name = "miow"
+version = "0.2.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "ebd808424166322d4a38da87083bfddd3ac4c131334ed55856112eb06d46944d"
+dependencies = [
+ "kernel32-sys",
+ "net2",
+ "winapi 0.2.8",
+ "ws2_32-sys",
]
[[package]]
@@ -544,7 +819,7 @@ version = "0.3.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b9f1c5b025cda876f66ef43a113f91ebc9f4ccef34843000e0adf6ebbab84e21"
dependencies = [
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -566,12 +841,23 @@ dependencies = [
]
[[package]]
+name = "net2"
+version = "0.2.37"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "391630d12b68002ae1e25e8f974306474966550ad82dac6886fb8910c19568ae"
+dependencies = [
+ "cfg-if 0.1.10",
+ "libc",
+ "winapi 0.3.9",
+]
+
+[[package]]
name = "ntapi"
version = "0.3.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3f6bb902e437b6d86e03cce10a7e2af662292c5dfef23b65899ea3ac9354ad44"
dependencies = [
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -616,7 +902,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0c7ae222234c30df141154f159066c5093ff73b63204dcda7121eb082fc56a95"
dependencies = [
"bitflags",
- "cfg-if",
+ "cfg-if 1.0.0",
"foreign-types",
"libc",
"once_cell",
@@ -643,6 +929,32 @@ dependencies = [
]
[[package]]
+name = "parking_lot"
+version = "0.9.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "f842b1982eb6c2fe34036a4fbfb06dd185a3f5c8edfaacdf7d1ea10b07de6252"
+dependencies = [
+ "lock_api",
+ "parking_lot_core",
+ "rustc_version",
+]
+
+[[package]]
+name = "parking_lot_core"
+version = "0.6.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "b876b1b9e7ac6e1a74a6da34d25c42e17e8862aa409cbbbdcfc8d86c6f3bc62b"
+dependencies = [
+ "cfg-if 0.1.10",
+ "cloudabi",
+ "libc",
+ "redox_syscall 0.1.57",
+ "rustc_version",
+ "smallvec",
+ "winapi 0.3.9",
+]
+
+[[package]]
name = "percent-encoding"
version = "2.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -773,6 +1085,12 @@ dependencies = [
[[package]]
name = "redox_syscall"
+version = "0.1.57"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "41cc0f7e4d5d4544e8861606a285bb08d3e70712ccc7d2b84d7c0ccfaf4b05ce"
+
+[[package]]
+name = "redox_syscall"
version = "0.2.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8383f39639269cde97d255a32bdb68c047337295414940c68bdd30c2e13203ff"
@@ -803,7 +1121,7 @@ version = "0.5.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3acd125665422973a33ac9d3dd2df85edad0f4ae9b00dafb1a05e43a9f5ef8e7"
dependencies = [
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -813,13 +1131,13 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "07bea77bc708afa10e59905c3d4af7c8fd43c9214251673095ff8b14345fcbc5"
dependencies = [
"base64",
- "bytes",
+ "bytes 1.1.0",
"encoding_rs",
"futures-core",
"futures-util",
- "http",
- "http-body",
- "hyper",
+ "http 0.2.5",
+ "http-body 0.4.4",
+ "hyper 0.14.15",
"hyper-tls",
"ipnet",
"js-sys",
@@ -832,7 +1150,7 @@ dependencies = [
"serde",
"serde_json",
"serde_urlencoded",
- "tokio",
+ "tokio 1.14.0",
"tokio-native-tls",
"url",
"wasm-bindgen",
@@ -853,7 +1171,7 @@ dependencies = [
"spin",
"untrusted",
"web-sys",
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -912,10 +1230,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8f05ba609c234e60bee0d547fe94a4c7e9da733d1c962cf6e59efa4cd9c8bc75"
dependencies = [
"lazy_static",
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
+name = "scopeguard"
+version = "1.1.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd"
+
+[[package]]
name = "sct"
version = "0.6.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -1038,13 +1362,22 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9def91fd1e018fe007022791f865d0ccc9b3a0d5001e01aabb8b40e46000afb5"
[[package]]
+name = "smallvec"
+version = "0.6.14"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "b97fcaeba89edba30f044a10c6a3cc39df9c3f17d7cd829dd1446cab35f890e0"
+dependencies = [
+ "maybe-uninit",
+]
+
+[[package]]
name = "socket2"
version = "0.4.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5dc90fe6c7be1a323296982db1836d1ea9e47b6839496dde9a541bc496df3516"
dependencies = [
"libc",
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -1112,6 +1445,15 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "213701ba3370744dcd1a12960caa4843b3d68b4d1c0a5d575e0d65b2ee9d16c0"
[[package]]
+name = "string"
+version = "0.2.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "d24114bfcceb867ca7f71a0d3fe45d45619ec47a6fbfa98cb14e14250bfa5d6d"
+dependencies = [
+ "bytes 0.4.12",
+]
+
+[[package]]
name = "syn"
version = "1.0.82"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -1128,12 +1470,12 @@ 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",
- "redox_syscall",
+ "redox_syscall 0.2.10",
"remove_dir_all",
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -1152,7 +1494,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ca8a50ef2360fbd1eeb0ecd46795a87a19024eb4b53c5dc916ca1fd95fe62438"
dependencies = [
"libc",
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -1167,7 +1509,7 @@ dependencies = [
"stdweb",
"time-macros",
"version_check",
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -1210,21 +1552,81 @@ checksum = "cda74da7e1a664f795bb1f8a87ec406fb89a02522cf6e50620d016add6dbbf5c"
[[package]]
name = "tokio"
+version = "0.1.22"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "5a09c0b5bb588872ab2f09afa13ee6e9dac11e10a0ec9e8e3ba39a5a5d530af6"
+dependencies = [
+ "bytes 0.4.12",
+ "futures 0.1.31",
+ "mio 0.6.23",
+ "num_cpus",
+ "tokio-current-thread",
+ "tokio-executor",
+ "tokio-io",
+ "tokio-reactor",
+ "tokio-threadpool",
+ "tokio-timer",
+]
+
+[[package]]
+name = "tokio"
version = "1.14.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "70e992e41e0d2fb9f755b37446f20900f64446ef54874f40a60c78f021ac6144"
dependencies = [
"autocfg",
- "bytes",
+ "bytes 1.1.0",
"libc",
"memchr",
- "mio",
+ "mio 0.7.14",
"num_cpus",
"once_cell",
"pin-project-lite",
"signal-hook-registry",
"tokio-macros",
- "winapi",
+ "winapi 0.3.9",
+]
+
+[[package]]
+name = "tokio-buf"
+version = "0.1.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "8fb220f46c53859a4b7ec083e41dec9778ff0b1851c0942b211edb89e0ccdc46"
+dependencies = [
+ "bytes 0.4.12",
+ "either",
+ "futures 0.1.31",
+]
+
+[[package]]
+name = "tokio-current-thread"
+version = "0.1.7"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "b1de0e32a83f131e002238d7ccde18211c0a5397f60cbfffcb112868c2e0e20e"
+dependencies = [
+ "futures 0.1.31",
+ "tokio-executor",
+]
+
+[[package]]
+name = "tokio-executor"
+version = "0.1.10"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "fb2d1b8f4548dbf5e1f7818512e9c406860678f29c300cdf0ebac72d1a3a1671"
+dependencies = [
+ "crossbeam-utils",
+ "futures 0.1.31",
+]
+
+[[package]]
+name = "tokio-io"
+version = "0.1.13"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "57fc868aae093479e3131e3d165c93b1c7474109d13c90ec0dda2a1bbfff0674"
+dependencies = [
+ "bytes 0.4.12",
+ "futures 0.1.31",
+ "log",
]
[[package]]
@@ -1245,7 +1647,90 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f7d995660bd2b7f8c1568414c1126076c13fbb725c40112dc0120b78eb9b717b"
dependencies = [
"native-tls",
- "tokio",
+ "tokio 1.14.0",
+]
+
+[[package]]
+name = "tokio-reactor"
+version = "0.1.12"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "09bc590ec4ba8ba87652da2068d150dcada2cfa2e07faae270a5e0409aa51351"
+dependencies = [
+ "crossbeam-utils",
+ "futures 0.1.31",
+ "lazy_static",
+ "log",
+ "mio 0.6.23",
+ "num_cpus",
+ "parking_lot",
+ "slab",
+ "tokio-executor",
+ "tokio-io",
+ "tokio-sync",
+]
+
+[[package]]
+name = "tokio-rustls"
+version = "0.23.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "4baa378e417d780beff82bf54ceb0d195193ea6a00c14e22359e7f39456b5689"
+dependencies = [
+ "rustls 0.20.2",
+ "tokio 1.14.0",
+ "webpki 0.22.0",
+]
+
+[[package]]
+name = "tokio-sync"
+version = "0.1.8"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "edfe50152bc8164fcc456dab7891fa9bf8beaf01c5ee7e1dd43a397c3cf87dee"
+dependencies = [
+ "fnv",
+ "futures 0.1.31",
+]
+
+[[package]]
+name = "tokio-tcp"
+version = "0.1.4"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "98df18ed66e3b72e742f185882a9e201892407957e45fbff8da17ae7a7c51f72"
+dependencies = [
+ "bytes 0.4.12",
+ "futures 0.1.31",
+ "iovec",
+ "mio 0.6.23",
+ "tokio-io",
+ "tokio-reactor",
+]
+
+[[package]]
+name = "tokio-threadpool"
+version = "0.1.18"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "df720b6581784c118f0eb4310796b12b1d242a7eb95f716a8367855325c25f89"
+dependencies = [
+ "crossbeam-deque",
+ "crossbeam-queue",
+ "crossbeam-utils",
+ "futures 0.1.31",
+ "lazy_static",
+ "log",
+ "num_cpus",
+ "slab",
+ "tokio-executor",
+]
+
+[[package]]
+name = "tokio-timer"
+version = "0.2.13"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "93044f2d313c95ff1cb7809ce9a7a05735b012288a888b62d4434fd58c94f296"
+dependencies = [
+ "crossbeam-utils",
+ "futures 0.1.31",
+ "slab",
+ "tokio-executor",
]
[[package]]
@@ -1254,12 +1739,12 @@ version = "0.6.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9e99e1983e5d376cd8eb4b66604d2e99e79f5bd988c3055891dcd8c9e2604cc0"
dependencies = [
- "bytes",
+ "bytes 1.1.0",
"futures-core",
"futures-sink",
"log",
"pin-project-lite",
- "tokio",
+ "tokio 1.14.0",
]
[[package]]
@@ -1274,7 +1759,7 @@ version = "0.1.29"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "375a639232caf30edfc78e8d89b2d4c375515393e7af7e16f01cd96917fb2105"
dependencies = [
- "cfg-if",
+ "cfg-if 1.0.0",
"pin-project-lite",
"tracing-core",
]
@@ -1294,12 +1779,15 @@ version = "0.1.0"
dependencies = [
"acme-micro",
"anyhow",
- "bytes",
+ "bytes 1.1.0",
"chrono",
"envy",
- "futures",
- "http",
- "hyper",
+ "futures 0.3.18",
+ "futures-util",
+ "http 0.2.5",
+ "hyper 0.14.15",
+ "hyper-reverse-proxy",
+ "lazy_static",
"log",
"pretty_env_logger",
"regex",
@@ -1308,7 +1796,9 @@ dependencies = [
"rustls-pemfile",
"serde",
"serde_json",
- "tokio",
+ "tokio 1.14.0",
+ "tokio-rustls",
+ "unicase",
"uuid",
]
@@ -1319,6 +1809,15 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "59547bce71d9c38b83d9c0e92b6066c4253371f15005def0c30d9657f50c7642"
[[package]]
+name = "unicase"
+version = "2.6.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "50f37be617794602aabbeee0be4f259dc1778fabe05e2d67ee8f79326d5cb4f6"
+dependencies = [
+ "version_check",
+]
+
+[[package]]
name = "unicode-bidi"
version = "0.3.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -1396,6 +1895,17 @@ checksum = "5fecdca9a5291cc2b8dcf7dc02453fee791a280f3743cb0905f8822ae463b3fe"
[[package]]
name = "want"
+version = "0.2.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "b6395efa4784b027708f7451087e647ec73cc74f5d9bc2e418404248d679a230"
+dependencies = [
+ "futures 0.1.31",
+ "log",
+ "try-lock",
+]
+
+[[package]]
+name = "want"
version = "0.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1ce8a968cb1cd110d136ff8b819a556d6fb6d919363c61534f6860c7eb172ba0"
@@ -1416,7 +1926,7 @@ version = "0.2.78"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "632f73e236b219150ea279196e54e610f5dbafa5d61786303d4da54f84e47fce"
dependencies = [
- "cfg-if",
+ "cfg-if 1.0.0",
"wasm-bindgen-macro",
]
@@ -1441,7 +1951,7 @@ version = "0.4.28"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8e8d7523cb1f2a4c96c1317ca690031b714a51cc14e05f712446691f413f5d39"
dependencies = [
- "cfg-if",
+ "cfg-if 1.0.0",
"js-sys",
"wasm-bindgen",
"web-sys",
@@ -1517,6 +2027,12 @@ dependencies = [
[[package]]
name = "winapi"
+version = "0.2.8"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a"
+
+[[package]]
+name = "winapi"
version = "0.3.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419"
@@ -1526,6 +2042,12 @@ dependencies = [
]
[[package]]
+name = "winapi-build"
+version = "0.1.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc"
+
+[[package]]
name = "winapi-i686-pc-windows-gnu"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -1537,7 +2059,7 @@ version = "0.1.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "70ec6ce85bb158151cae5e5c87f95a8e97d2c0c4b001223f33a334e3ce5de178"
dependencies = [
- "winapi",
+ "winapi 0.3.9",
]
[[package]]
@@ -1552,5 +2074,15 @@ version = "0.7.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0120db82e8a1e0b9fb3345a539c478767c0048d842860994d96113d5b667bd69"
dependencies = [
- "winapi",
+ "winapi 0.3.9",
+]
+
+[[package]]
+name = "ws2_32-sys"
+version = "0.2.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "d59cefebd0c892fa2dd6de581e937301d8552cb44489cdff035c6187cb63fa5e"
+dependencies = [
+ "winapi 0.2.8",
+ "winapi-build",
]
diff --git a/Cargo.toml b/Cargo.toml
index 8de31a0..9c7ae8a 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -23,5 +23,11 @@ uuid = "0.8"
rustls = "0.20"
rustls-pemfile = "0.2"
chrono = { version = "0.4", features = [ "serde" ] }
-hyper = { version = "0.14", features = [ "http1", "http2", "runtime", "server", "tcp" ] }
+hyper = { version = "0.14", features = [ "full" ] }
+futures-util = "0.3"
+tokio-rustls = "0.23"
+#hyper-rustls = "0.23"
http = "0.2"
+hyper-reverse-proxy = "0.4"
+unicase = "2"
+lazy_static = "1.4"
diff --git a/src/cert.rs b/src/cert.rs
index de0d821..0be43f3 100644
--- a/src/cert.rs
+++ b/src/cert.rs
@@ -1,3 +1,5 @@
+use std::sync::Arc;
+
use anyhow::Result;
use chrono::{Date, NaiveDate, Utc};
@@ -17,7 +19,7 @@ pub struct CertSer {
pub struct Cert {
pub ser: CertSer,
- pub certkey: CertifiedKey,
+ pub certkey: Arc<CertifiedKey>,
}
impl Cert {
@@ -46,7 +48,7 @@ impl Cert {
bail!("{} keys present in pem file", keys.len());
}
- let certkey = CertifiedKey::new(certs, keys.into_iter().next().unwrap());
+ let certkey = Arc::new(CertifiedKey::new(certs, keys.into_iter().next().unwrap()));
Ok(Cert { ser, certkey })
}
diff --git a/src/cert_store.rs b/src/cert_store.rs
index 6529395..1b1a478 100644
--- a/src/cert_store.rs
+++ b/src/cert_store.rs
@@ -6,9 +6,11 @@ use anyhow::Result;
use chrono::Utc;
use log::*;
use tokio::sync::watch;
+use tokio::task::block_in_place;
use acme_micro::create_p384_key;
use acme_micro::{Directory, DirectoryUrl};
+use rustls::sign::CertifiedKey;
use crate::cert::{Cert, CertSer};
use crate::consul::Consul;
@@ -93,7 +95,7 @@ impl CertStore {
dir.load_account(std::str::from_utf8(&acc_privkey)?, contact)?
} else {
info!("Creating new Let's encrypt account");
- let acc = dir.register_account(contact.clone())?;
+ let acc = block_in_place(|| dir.register_account(contact.clone()))?;
self.consul
.kv_put(
"letsencrypt_account_key.pem",
@@ -119,17 +121,18 @@ impl CertStore {
.await?;
info!("Validating challenge");
- chall.validate(Duration::from_millis(5000))?;
+ block_in_place(|| chall.validate(Duration::from_millis(5000)))?;
info!("Deleting challenge");
self.consul.kv_delete(&chall_key).await?;
- ord_new.refresh()?;
+ block_in_place(|| ord_new.refresh())?;
};
let pkey_pri = create_p384_key()?;
- let ord_cert = ord_csr.finalize_pkey(pkey_pri, Duration::from_millis(5000))?;
- let cert = ord_cert.download_cert()?;
+ let ord_cert =
+ block_in_place(|| ord_csr.finalize_pkey(pkey_pri, Duration::from_millis(5000)))?;
+ let cert = block_in_place(|| ord_cert.download_cert())?;
info!("Keys and certificate obtained");
let key_pem = cert.private_key().to_string();
@@ -157,3 +160,13 @@ impl CertStore {
Ok(cert)
}
}
+
+pub struct StoreResolver(pub Arc<CertStore>);
+
+impl rustls::server::ResolvesServerCert for StoreResolver {
+ fn resolve(&self, client_hello: rustls::server::ClientHello<'_>) -> Option<Arc<CertifiedKey>> {
+ let domain = client_hello.server_name()?;
+ let cert = futures::executor::block_on(self.0.get_cert(domain)).ok()?;
+ Some(cert.certkey.clone())
+ }
+}
diff --git a/src/https.rs b/src/https.rs
new file mode 100644
index 0000000..c80d51c
--- /dev/null
+++ b/src/https.rs
@@ -0,0 +1,126 @@
+use std::net::SocketAddr;
+use std::sync::Arc;
+
+use anyhow::Result;
+use log::*;
+
+use futures::FutureExt;
+use hyper::server::conn::Http;
+use hyper::service::service_fn;
+use hyper::{Body, Request, Response, StatusCode};
+use tokio::net::TcpListener;
+use tokio::sync::watch;
+use tokio_rustls::TlsAcceptor;
+
+use crate::cert_store::{CertStore, StoreResolver};
+use crate::proxy_config::ProxyConfig;
+use crate::reverse_proxy;
+
+pub async fn serve_https(
+ cert_store: Arc<CertStore>,
+ proxy_config: watch::Receiver<Arc<ProxyConfig>>,
+) -> Result<()> {
+ let addr = format!("0.0.0.0:1443");
+
+ let mut cfg = rustls::ServerConfig::builder()
+ .with_safe_defaults()
+ .with_no_client_auth()
+ .with_cert_resolver(Arc::new(StoreResolver(cert_store)));
+
+ cfg.alpn_protocols = vec![b"h2".to_vec(), b"http/1.1".to_vec()];
+ let tls_cfg = Arc::new(cfg);
+ let tls_acceptor = Arc::new(TlsAcceptor::from(tls_cfg));
+
+ println!("Starting to serve on https://{}.", addr);
+
+ let tcp = TcpListener::bind(&addr).await?;
+ loop {
+ let (socket, remote_addr) = tcp.accept().await?;
+
+ let proxy_config = proxy_config.clone();
+ let tls_acceptor = tls_acceptor.clone();
+
+ tokio::spawn(async move {
+ match tls_acceptor.accept(socket).await {
+ Ok(stream) => {
+ debug!("TLS handshake was successfull");
+ let http_result = Http::new()
+ .serve_connection(
+ stream,
+ service_fn(move |req: Request<Body>| {
+ let proxy_config: Arc<ProxyConfig> = proxy_config.borrow().clone();
+ handle(remote_addr, req, proxy_config).map(|res| match res {
+ Err(e) => {
+ warn!("Handler error: {}", e);
+ Response::builder()
+ .status(StatusCode::INTERNAL_SERVER_ERROR)
+ .body(Body::from(format!("{}", e)))
+ .map_err(Into::into)
+ }
+ x => x,
+ })
+ }),
+ )
+ .await;
+ if let Err(http_err) = http_result {
+ debug!("HTTP error: {}", http_err);
+ }
+ }
+ Err(e) => debug!("Error in TLS connection: {}", e),
+ }
+ });
+ }
+}
+
+// Custom echo service, handling two different routes and a
+// catch-all 404 responder.
+async fn handle(
+ remote_addr: SocketAddr,
+ req: Request<Body>,
+ proxy_config: Arc<ProxyConfig>,
+) -> Result<Response<Body>, anyhow::Error> {
+ let host = if let Some(auth) = req.uri().authority() {
+ auth.as_str()
+ } else {
+ req.headers()
+ .get("host")
+ .ok_or_else(|| anyhow!("Missing host header"))?
+ .to_str()?
+ };
+ let path = req.uri().path();
+
+ let ent = proxy_config
+ .entries
+ .iter()
+ .filter(|ent| {
+ ent.host == host
+ && ent
+ .path_prefix
+ .as_ref()
+ .map(|prefix| path.starts_with(prefix))
+ .unwrap_or(true)
+ })
+ .min_by_key(|ent| {
+ (
+ ent.priority,
+ -(ent
+ .path_prefix
+ .as_ref()
+ .map(|x| x.len() as i32)
+ .unwrap_or(0)),
+ )
+ });
+
+ if let Some(proxy_to) = ent {
+ let to_addr = format!("http://{}", proxy_to.target_addr);
+ info!("Proxying {} {} -> {}", host, path, to_addr);
+
+ reverse_proxy::call(remote_addr.ip(), &to_addr, req).await
+ } else {
+ info!("Proxying {} {} -> NOT FOUND", host, path);
+
+ Ok(Response::builder()
+ .status(StatusCode::NOT_FOUND)
+ .body(Body::from("No matching proxy entry"))?)
+ }
+}
diff --git a/src/main.rs b/src/main.rs
index d7f1e24..df0845d 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -5,11 +5,13 @@ mod cert;
mod cert_store;
mod consul;
mod http;
+mod https;
mod proxy_config;
+mod reverse_proxy;
use log::*;
-#[tokio::main(flavor = "multi_thread")]
+#[tokio::main(flavor = "multi_thread", worker_threads = 10)]
async fn main() {
if std::env::var("RUST_LOG").is_err() {
std::env::set_var("RUST_LOG", "tricot=debug")
@@ -28,6 +30,10 @@ async fn main() {
);
tokio::spawn(http::serve_http(consul.clone()));
+ tokio::spawn(https::serve_https(
+ cert_store.clone(),
+ rx_proxy_config.clone(),
+ ));
while rx_proxy_config.changed().await.is_ok() {
info!("Proxy config: {:#?}", *rx_proxy_config.borrow());
diff --git a/src/reverse_proxy.rs b/src/reverse_proxy.rs
new file mode 100644
index 0000000..82533d8
--- /dev/null
+++ b/src/reverse_proxy.rs
@@ -0,0 +1,114 @@
+//! Copied from https://github.com/felipenoris/hyper-reverse-proxy
+//! See there for original Copyright notice
+
+use anyhow::Result;
+
+use hyper::header::{HeaderMap, HeaderValue};
+use hyper::{Body, Client, Request, Response, Uri};
+use lazy_static::lazy_static;
+use std::net::IpAddr;
+use std::str::FromStr;
+
+fn is_hop_header(name: &str) -> bool {
+ use unicase::Ascii;
+
+ // A list of the headers, using `unicase` to help us compare without
+ // worrying about the case, and `lazy_static!` to prevent reallocation
+ // of the vector.
+ lazy_static! {
+ static ref HOP_HEADERS: Vec<Ascii<&'static str>> = vec![
+ Ascii::new("Connection"),
+ Ascii::new("Keep-Alive"),
+ Ascii::new("Proxy-Authenticate"),
+ Ascii::new("Proxy-Authorization"),
+ Ascii::new("Te"),
+ Ascii::new("Trailers"),
+ Ascii::new("Transfer-Encoding"),
+ Ascii::new("Upgrade"),
+ ];
+ }
+
+ HOP_HEADERS.iter().any(|h| h == &name)
+}
+
+/// Returns a clone of the headers without the [hop-by-hop headers].
+///
+/// [hop-by-hop headers]: http://www.w3.org/Protocols/rfc2616/rfc2616-sec13.html
+fn remove_hop_headers(headers: &HeaderMap<HeaderValue>) -> HeaderMap<HeaderValue> {
+ let mut result = HeaderMap::new();
+ for (k, v) in headers.iter() {
+ if !is_hop_header(k.as_str()) {
+ result.insert(k.clone(), v.clone());
+ }
+ }
+ result
+}
+
+fn create_proxied_response<B>(mut response: Response<B>) -> Response<B> {
+ *response.headers_mut() = remove_hop_headers(response.headers());
+ response
+}
+
+fn forward_uri<B>(forward_url: &str, req: &Request<B>) -> Result<Uri> {
+ let forward_uri = match req.uri().query() {
+ Some(query) => format!("{}{}?{}", forward_url, req.uri().path(), query),
+ None => format!("{}{}", forward_url, req.uri().path()),
+ };
+
+ Ok(Uri::from_str(forward_uri.as_str())?)
+}
+
+fn create_proxied_request<B>(
+ client_ip: IpAddr,
+ forward_url: &str,
+ request: Request<B>,
+) -> Result<Request<B>> {
+ let mut builder = Request::builder().uri(forward_uri(forward_url, &request)?);
+
+ *builder.headers_mut().unwrap() = remove_hop_headers(request.headers());
+
+ let host_header_name = "host";
+ let x_forwarded_for_header_name = "x-forwarded-for";
+
+ // If request does not have host header, add it from original URI authority
+ if let Some(authority) = request.uri().authority() {
+ if let hyper::header::Entry::Vacant(entry) = builder
+ .headers_mut()
+ .unwrap()
+ .entry(host_header_name)
+ {
+ entry.insert(authority.as_str().parse()?);
+ }
+ }
+
+ // Add forwarding information in the headers
+ match builder
+ .headers_mut()
+ .unwrap()
+ .entry(x_forwarded_for_header_name)
+ {
+ hyper::header::Entry::Vacant(entry) => {
+ entry.insert(client_ip.to_string().parse()?);
+ }
+
+ hyper::header::Entry::Occupied(mut entry) => {
+ let addr = format!("{}, {}", entry.get().to_str()?, client_ip);
+ entry.insert(addr.parse()?);
+ }
+ }
+
+ Ok(builder.body(request.into_body())?)
+}
+
+pub async fn call(
+ client_ip: IpAddr,
+ forward_uri: &str,
+ request: Request<Body>,
+) -> Result<Response<Body>> {
+ let proxied_request = create_proxied_request(client_ip, &forward_uri, request)?;
+
+ let client = Client::new();
+ let response = client.request(proxied_request).await?;
+ let proxied_response = create_proxied_response(response);
+ Ok(proxied_response)
+}