rust_pop3_client/
pop3_connection_factory.rs1use std::sync::Arc;
2use std::net::TcpStream;
3use std::error::Error;
4
5use rustls::pki_types::ServerName;
6use rustls::{RootCertStore, ClientConnection, StreamOwned};
7
8use crate::LineReader;
9use crate::Pop3ConnectionImpl;
10
11pub struct Pop3ConnectionFactory {
12
13}
14
15impl Pop3ConnectionFactory {
16 pub fn new(host: &str, port: u16) -> Result<Pop3ConnectionImpl<StreamOwned<ClientConnection, TcpStream>>, Box<dyn Error>> {
23 let mut root_store = RootCertStore::empty();
24 for cert in rustls_native_certs::load_native_certs().certs {
25 root_store.add(cert)?;
26 }
27
28 Pop3ConnectionFactory::with_custom_certs(host, port, root_store)
29 }
30
31 pub fn with_custom_certs(host: &str, port: u16, root_store: RootCertStore) -> Result<Pop3ConnectionImpl<StreamOwned<ClientConnection, TcpStream>>, Box<dyn Error>> {
53 let config = rustls::ClientConfig::builder()
54 .with_root_certificates(root_store)
55 .with_no_client_auth();
56
57 let server_name = ServerName::try_from(host)?;
58
59 let connection = rustls::ClientConnection::new(Arc::new(config), server_name.to_owned())?;
60 let stream = TcpStream::connect(format!("{}:{}", host, port))?;
61 let stream = rustls::StreamOwned::new(connection, stream);
62
63 let mut client = Pop3ConnectionImpl {
64 stream,
65 reader: LineReader::new()
66 };
67
68 client.read_status_line()?;
69 Ok(client)
70 }
71
72 pub fn without_tls(host: &str, port: u16) -> Result<Pop3ConnectionImpl<TcpStream>, Box<dyn Error>> {
79 let stream = TcpStream::connect(format!("{}:{}", host, port))?;
80 let mut client = Pop3ConnectionImpl {
81 stream,
82 reader: LineReader::new()
83 };
84 client.read_status_line()?;
85 Ok(client)
86 }
87
88}