diff --git a/Cargo.toml b/Cargo.toml index cd2b812..e2d405c 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "telexide" -version = "0.1.12" +version = "0.1.13" description = "An async Rust library for the telegram bot API." documentation = "https://docs.rs/telexide" repository = "https://github.com/callieve/telexide" @@ -11,6 +11,12 @@ readme = "README.md" authors = ["Calli <me@calli.dev>"] edition = "2021" +[features] +default = ["rustls"] + +native-tls = ["dep:hyper-tls"] +rustls = ["dep:hyper-rustls"] + [dependencies.telexide_proc_macros] path = "./telexide_proc_macros" version = "0.1.1" @@ -20,7 +26,8 @@ serde = { version = "1.0", features = ["derive"] } serde_json = "1.0" chrono = "0.4" hyper = { version = "0.14", features = ["http2", "client", "server"] } -hyper-tls = "0.5" +hyper-tls = { version = "0.5", optional = true } +hyper-rustls = { version = "0.23", optional = true } tokio = { version = "1.3", features = ["rt", "net", "time", "macros", "sync", "signal", "rt-multi-thread"] } http = "^0.2.3" async-trait = "0.1" diff --git a/README.md b/README.md index 90927f7..34f9823 100644 --- a/README.md +++ b/README.md @@ -59,7 +59,7 @@ async fn main() -> telexide::Result<()> { For more examples, please see the examples directory. -## Features +## Crate Features - [x] Supports all of the telegram bot API, up to and including version 6.5 - [x] easy to use and customisable client @@ -89,9 +89,17 @@ Add the following to your `Cargo.toml` file: ```toml [dependencies] -telexide = "0.1.12" +telexide = "0.1.13" ``` +### Feature Flags + +Telexide uses a set of [feature flags] to allow switching between rustls and native-tls for tls support. +In the future flags may be added to enable/disable optional parts of the crate. + +- `rustls`: Makes the api client use `hyper-rustls` to create the tls connector. Enabled by default. +- `native-tls`: Makes the api client use `hyper-tls` to create the tls connector. Overwrites the `rustls` feature if enabled. + ## Supported Rust Versions The minimum supported version is 1.63. The current Telexide version is not guaranteed to build on Rust versions earlier than the minimum supported version. @@ -108,3 +116,4 @@ The minimum supported version is 1.63. The current Telexide version is not guara [tg_commands]: https://core.telegram.org/bots#commands [`framework`]: https://docs.rs/telexide/*/telexide/framework/struct.Framework.html [framework]: https://docs.rs/telexide/*/telexide/framework/index.html +[feature flags]: https://doc.rust-lang.org/cargo/reference/features.html#the-features-section diff --git a/examples/repeat_image/Cargo.toml b/examples/repeat_image/Cargo.toml index 5cc9357..6ce08ac 100644 --- a/examples/repeat_image/Cargo.toml +++ b/examples/repeat_image/Cargo.toml @@ -5,7 +5,7 @@ authors = ["my name <my@email.address>"] edition = "2021" [dependencies] -telexide = { path = "../../" } +telexide = { path = "../../", features = ["native-tls"]} tokio = { version = "1", features = ["full"] } typemap_rev = "0.3.0" parking_lot = "0.12" diff --git a/src/api/api_client.rs b/src/api/api_client.rs index d971b50..0b3c5d8 100644 --- a/src/api/api_client.rs +++ b/src/api/api_client.rs @@ -8,6 +8,11 @@ use std::io::Write; static TELEGRAM_API: &str = "https://api.telegram.org/bot"; +#[cfg(feature = "native-tls")] +pub type TlsClient = Client<hyper_tls::HttpsConnector<HttpConnector>>; +#[cfg(all(feature = "rustls", not(feature = "native-tls")))] +pub type TlsClient = Client<hyper_rustls::HttpsConnector<HttpConnector>>; + /// A default implementation of the [`API`] trait. /// /// It requires your bot token in order to interact with the telegram API and @@ -33,7 +38,7 @@ static TELEGRAM_API: &str = "https://api.telegram.org/bot"; /// /// [`Client`]: ../client/struct.Client.html pub struct APIClient { - hyper_client: Client<hyper_tls::HttpsConnector<HttpConnector>>, + hyper_client: TlsClient, token: String, } @@ -41,13 +46,10 @@ impl APIClient { /// Creates a new `APIClient` with the provided token and hyper client (if /// it is Some). #[allow(clippy::needless_pass_by_value)] - pub fn new( - hyper_client: Option<Client<hyper_tls::HttpsConnector<HttpConnector>>>, - token: impl ToString, - ) -> Self { + pub fn new(hyper_client: Option<TlsClient>, token: impl ToString) -> Self { hyper_client.map_or_else( || Self { - hyper_client: hyper::Client::builder().build(hyper_tls::HttpsConnector::new()), + hyper_client: Self::make_default_client(), token: token.to_string(), }, |c| Self { @@ -57,6 +59,22 @@ impl APIClient { ) } + #[cfg(feature = "native-tls")] + fn make_default_client() -> TlsClient { + hyper::Client::builder().build(hyper_tls::HttpsConnector::new()) + } + + #[cfg(all(feature = "rustls", not(feature = "native-tls")))] + fn make_default_client() -> TlsClient { + hyper::Client::builder().build( + hyper_rustls::HttpsConnectorBuilder::new() + .with_native_roots() + .https_or_http() + .enable_http1() + .build(), + ) + } + /// Creates a new `APIClient` with the provided token and the default hyper /// client. #[allow(clippy::needless_pass_by_value)] @@ -88,7 +106,7 @@ impl APIClient { /// gets a reference to the underlying hyper client, for example so you can /// make custom api requests - pub fn get_hyper(&self) -> &Client<hyper_tls::HttpsConnector<HttpConnector>> { + pub fn get_hyper(&self) -> &TlsClient { &self.hyper_client } } diff --git a/src/api/mod.rs b/src/api/mod.rs index d314665..7c8feb0 100644 --- a/src/api/mod.rs +++ b/src/api/mod.rs @@ -12,5 +12,6 @@ pub mod types; pub use api::API; pub use api_client::APIClient; +pub use api_client::TlsClient; pub use endpoints::APIEndpoint; pub use response::Response; diff --git a/src/client/builder.rs b/src/client/builder.rs index 4cb6767..f072662 100644 --- a/src/client/builder.rs +++ b/src/client/builder.rs @@ -1,6 +1,6 @@ use super::{APIConnector, Client, EventHandlerFunc, RawEventHandlerFunc, WebhookOptions}; use crate::{ - api::{types::UpdateType, APIClient}, + api::{types::UpdateType, APIClient, TlsClient}, framework::Framework, }; @@ -10,7 +10,7 @@ use typemap_rev::TypeMap; /// A builder for the [`Client`] object to make customisation easier pub struct ClientBuilder { - hyper_client: Option<hyper::Client<hyper_tls::HttpsConnector<hyper::client::HttpConnector>>>, + hyper_client: Option<TlsClient>, api_client: Option<Arc<Box<APIConnector>>>, webhook: Option<WebhookOptions>, framework: Option<Arc<Framework>>, @@ -60,10 +60,7 @@ impl ClientBuilder { } /// Sets the custom hyper client for the `APIClient` to use - pub fn set_hyper_client( - &mut self, - client: hyper::Client<hyper_tls::HttpsConnector<hyper::client::HttpConnector>>, - ) -> &mut Self { + pub fn set_hyper_client(&mut self, client: TlsClient) -> &mut Self { self.hyper_client = Some(client); self }