Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit60c1182

Browse files
committed
feat: add ssl_negotiation option
1 parent6ae17e0 commit60c1182

File tree

9 files changed

+111
-21
lines changed

9 files changed

+111
-21
lines changed

‎postgres/src/config.rs‎

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ use std::str::FromStr;
1010
use std::sync::Arc;
1111
use std::time::Duration;
1212
use tokio::runtime;
13+
use tokio_postgres::config::SslNegotiation;
1314
#[doc(inline)]
1415
pubuse tokio_postgres::config::{
1516
ChannelBinding,Host,LoadBalanceHosts,SslMode,TargetSessionAttrs,
@@ -40,6 +41,8 @@ use tokio_postgres::{Error, Socket};
4041
/// path to the directory containing Unix domain sockets. Otherwise, it is treated as a hostname. Multiple hosts
4142
/// can be specified, separated by commas. Each host will be tried in turn when connecting. Required if connecting
4243
/// with the `connect` method.
44+
/// * `sslnegotiation` - TLS negotiation method. If set to `direct`, the client will perform direct TLS handshake, this only works for PostgreSQL 17 and newer.
45+
/// If set to `postgres`, the default value, it follows original postgres wire protocol to perform the negotiation.
4346
/// * `hostaddr` - Numeric IP address of host to connect to. This should be in the standard IPv4 address format,
4447
/// e.g., 172.28.40.9. If your machine supports IPv6, you can also use those addresses.
4548
/// If this parameter is not specified, the value of `host` will be looked up to find the corresponding IP address,
@@ -230,6 +233,17 @@ impl Config {
230233
self.config.get_ssl_mode()
231234
}
232235

236+
/// Sets the SSL negotiation method
237+
pubfnssl_negotiation(&mutself,ssl_negotiation:SslNegotiation) ->&mutConfig{
238+
self.config.ssl_negotiation(ssl_negotiation);
239+
self
240+
}
241+
242+
/// Gets the SSL negotiation method
243+
pubfnget_ssl_negotiation(&self) ->SslNegotiation{
244+
self.config.get_ssl_negotiation()
245+
}
246+
233247
/// Adds a host to the configuration.
234248
///
235249
/// Multiple hosts can be specified by calling this method multiple times, and each will be tried in order. On Unix

‎tokio-postgres/src/cancel_query.rs‎

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,13 @@
11
usecrate::client::SocketConfig;
2-
usecrate::config::SslMode;
2+
usecrate::config::{SslMode,SslNegotiation};
33
usecrate::tls::MakeTlsConnect;
44
usecrate::{cancel_query_raw, connect_socket,Error,Socket};
55
use std::io;
66

77
pub(crate)asyncfncancel_query<T>(
88
config:Option<SocketConfig>,
99
ssl_mode:SslMode,
10+
ssl_negotiation:SslNegotiation,
1011
muttls:T,
1112
process_id:i32,
1213
secret_key:i32,
@@ -38,6 +39,14 @@ where
3839
)
3940
.await?;
4041

41-
cancel_query_raw::cancel_query_raw(socket, ssl_mode, tls, has_hostname, process_id, secret_key)
42-
.await
42+
cancel_query_raw::cancel_query_raw(
43+
socket,
44+
ssl_mode,
45+
ssl_negotiation,
46+
tls,
47+
has_hostname,
48+
process_id,
49+
secret_key,
50+
)
51+
.await
4352
}

‎tokio-postgres/src/cancel_query_raw.rs‎

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
usecrate::config::SslMode;
1+
usecrate::config::{SslMode,SslNegotiation};
22
usecrate::tls::TlsConnect;
33
usecrate::{connect_tls,Error};
44
use bytes::BytesMut;
@@ -8,6 +8,7 @@ use tokio::io::{AsyncRead, AsyncWrite, AsyncWriteExt};
88
pubasyncfncancel_query_raw<S,T>(
99
stream:S,
1010
mode:SslMode,
11+
negotiation:SslNegotiation,
1112
tls:T,
1213
has_hostname:bool,
1314
process_id:i32,
@@ -17,7 +18,7 @@ where
1718
S:AsyncRead +AsyncWrite +Unpin,
1819
T:TlsConnect<S>,
1920
{
20-
letmut stream = connect_tls::connect_tls(stream, mode, tls, has_hostname).await?;
21+
letmut stream = connect_tls::connect_tls(stream, mode,negotiation,tls, has_hostname).await?;
2122

2223
letmut buf =BytesMut::new();
2324
frontend::cancel_request(process_id, secret_key,&mut buf);

‎tokio-postgres/src/cancel_token.rs‎

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
usecrate::config::SslMode;
1+
usecrate::config::{SslMode,SslNegotiation};
22
usecrate::tls::TlsConnect;
33
#[cfg(feature ="runtime")]
44
usecrate::{cancel_query, client::SocketConfig, tls::MakeTlsConnect,Socket};
@@ -12,6 +12,7 @@ pub struct CancelToken {
1212
#[cfg(feature ="runtime")]
1313
pub(crate)socket_config:Option<SocketConfig>,
1414
pub(crate)ssl_mode:SslMode,
15+
pub(crate)ssl_negotiation:SslNegotiation,
1516
pub(crate)process_id:i32,
1617
pub(crate)secret_key:i32,
1718
}
@@ -37,6 +38,7 @@ impl CancelToken {
3738
cancel_query::cancel_query(
3839
self.socket_config.clone(),
3940
self.ssl_mode,
41+
self.ssl_negotiation,
4042
tls,
4143
self.process_id,
4244
self.secret_key,
@@ -54,6 +56,7 @@ impl CancelToken {
5456
cancel_query_raw::cancel_query_raw(
5557
stream,
5658
self.ssl_mode,
59+
self.ssl_negotiation,
5760
tls,
5861
true,
5962
self.process_id,

‎tokio-postgres/src/client.rs‎

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
usecrate::codec::BackendMessages;
2-
usecrate::config::SslMode;
2+
usecrate::config::{SslMode,SslNegotiation};
33
usecrate::connection::{Request,RequestMessages};
44
usecrate::copy_out::CopyOutStream;
55
#[cfg(feature ="runtime")]
@@ -180,6 +180,7 @@ pub struct Client {
180180
#[cfg(feature ="runtime")]
181181
socket_config:Option<SocketConfig>,
182182
ssl_mode:SslMode,
183+
ssl_negotiation:SslNegotiation,
183184
process_id:i32,
184185
secret_key:i32,
185186
}
@@ -188,6 +189,7 @@ impl Client {
188189
pub(crate)fnnew(
189190
sender: mpsc::UnboundedSender<Request>,
190191
ssl_mode:SslMode,
192+
ssl_negotiation:SslNegotiation,
191193
process_id:i32,
192194
secret_key:i32,
193195
) ->Client{
@@ -200,6 +202,7 @@ impl Client {
200202
#[cfg(feature ="runtime")]
201203
socket_config:None,
202204
ssl_mode,
205+
ssl_negotiation,
203206
process_id,
204207
secret_key,
205208
}
@@ -550,6 +553,7 @@ impl Client {
550553
#[cfg(feature ="runtime")]
551554
socket_config:self.socket_config.clone(),
552555
ssl_mode:self.ssl_mode,
556+
ssl_negotiation:self.ssl_negotiation,
553557
process_id:self.process_id,
554558
secret_key:self.secret_key,
555559
}

‎tokio-postgres/src/config.rs‎

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,16 @@ pub enum SslMode {
5050
Require,
5151
}
5252

53+
/// TLS negotiation configuration
54+
#[derive(Debug,Copy,Clone,PartialEq,Eq)]
55+
#[non_exhaustive]
56+
pubenumSslNegotiation{
57+
/// Use PostgreSQL SslRequest for Ssl negotiation
58+
Postgres,
59+
/// Start Ssl handshake without negotiation, only works for PostgreSQL 17+
60+
Direct,
61+
}
62+
5363
/// Channel binding configuration.
5464
#[derive(Debug,Copy,Clone,PartialEq,Eq)]
5565
#[non_exhaustive]
@@ -106,6 +116,8 @@ pub enum Host {
106116
/// path to the directory containing Unix domain sockets. Otherwise, it is treated as a hostname. Multiple hosts
107117
/// can be specified, separated by commas. Each host will be tried in turn when connecting. Required if connecting
108118
/// with the `connect` method.
119+
/// * `sslnegotiation` - TLS negotiation method. If set to `direct`, the client will perform direct TLS handshake, this only works for PostgreSQL 17 and newer.
120+
/// If set to `postgres`, the default value, it follows original postgres wire protocol to perform the negotiation.
109121
/// * `hostaddr` - Numeric IP address of host to connect to. This should be in the standard IPv4 address format,
110122
/// e.g., 172.28.40.9. If your machine supports IPv6, you can also use those addresses.
111123
/// If this parameter is not specified, the value of `host` will be looked up to find the corresponding IP address,
@@ -198,6 +210,7 @@ pub struct Config {
198210
pub(crate)options:Option<String>,
199211
pub(crate)application_name:Option<String>,
200212
pub(crate)ssl_mode:SslMode,
213+
pub(crate)ssl_negotiation:SslNegotiation,
201214
pub(crate)host:Vec<Host>,
202215
pub(crate)hostaddr:Vec<IpAddr>,
203216
pub(crate)port:Vec<u16>,
@@ -227,6 +240,7 @@ impl Config {
227240
options:None,
228241
application_name:None,
229242
ssl_mode:SslMode::Prefer,
243+
ssl_negotiation:SslNegotiation::Postgres,
230244
host:vec![],
231245
hostaddr:vec![],
232246
port:vec![],
@@ -325,6 +339,19 @@ impl Config {
325339
self.ssl_mode
326340
}
327341

342+
/// Sets the SSL negotiation method.
343+
///
344+
/// Defaults to `postgres`.
345+
pubfnssl_negotiation(&mutself,ssl_negotiation:SslNegotiation) ->&mutConfig{
346+
self.ssl_negotiation = ssl_negotiation;
347+
self
348+
}
349+
350+
/// Gets the SSL negotiation method.
351+
pubfnget_ssl_negotiation(&self) ->SslNegotiation{
352+
self.ssl_negotiation
353+
}
354+
328355
/// Adds a host to the configuration.
329356
///
330357
/// Multiple hosts can be specified by calling this method multiple times, and each will be tried in order. On Unix
@@ -550,6 +577,18 @@ impl Config {
550577
};
551578
self.ssl_mode(mode);
552579
}
580+
"sslnegotiation" =>{
581+
let mode =match value{
582+
"postgres" =>SslNegotiation::Postgres,
583+
"direct" =>SslNegotiation::Direct,
584+
_ =>{
585+
returnErr(Error::config_parse(Box::new(InvalidValue(
586+
"sslnegotiation",
587+
))))
588+
}
589+
};
590+
self.ssl_negotiation(mode);
591+
}
553592
"host" =>{
554593
for hostin value.split(','){
555594
self.host(host);

‎tokio-postgres/src/connect_raw.rs‎

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -89,7 +89,14 @@ where
8989
S:AsyncRead +AsyncWrite +Unpin,
9090
T:TlsConnect<S>,
9191
{
92-
let stream =connect_tls(stream, config.ssl_mode, tls, has_hostname).await?;
92+
let stream =connect_tls(
93+
stream,
94+
config.ssl_mode,
95+
config.ssl_negotiation,
96+
tls,
97+
has_hostname,
98+
)
99+
.await?;
93100

94101
letmut stream =StartupStream{
95102
inner:Framed::new(stream,PostgresCodec),
@@ -107,7 +114,13 @@ where
107114
let(process_id, secret_key, parameters) =read_info(&mut stream).await?;
108115

109116
let(sender, receiver) = mpsc::unbounded();
110-
let client =Client::new(sender, config.ssl_mode, process_id, secret_key);
117+
let client =Client::new(
118+
sender,
119+
config.ssl_mode,
120+
config.ssl_negotiation,
121+
process_id,
122+
secret_key,
123+
);
111124
let connection =Connection::new(stream.inner, stream.delayed, parameters, receiver);
112125

113126
Ok((client, connection))

‎tokio-postgres/src/connect_tls.rs‎

Lines changed: 14 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
usecrate::config::SslMode;
1+
usecrate::config::{SslMode,SslNegotiation};
22
usecrate::maybe_tls_stream::MaybeTlsStream;
33
usecrate::tls::private::ForcePrivateApi;
44
usecrate::tls::TlsConnect;
@@ -10,6 +10,7 @@ use tokio::io::{AsyncRead, AsyncReadExt, AsyncWrite, AsyncWriteExt};
1010
pubasyncfnconnect_tls<S,T>(
1111
mutstream:S,
1212
mode:SslMode,
13+
negotiation:SslNegotiation,
1314
tls:T,
1415
has_hostname:bool,
1516
) ->Result<MaybeTlsStream<S,T::Stream>,Error>
@@ -25,18 +26,20 @@ where
2526
SslMode::Prefer |SslMode::Require =>{}
2627
}
2728

28-
letmut buf =BytesMut::new();
29-
frontend::ssl_request(&mut buf);
30-
stream.write_all(&buf).await.map_err(Error::io)?;
29+
if negotiation ==SslNegotiation::Postgres{
30+
letmut buf =BytesMut::new();
31+
frontend::ssl_request(&mut buf);
32+
stream.write_all(&buf).await.map_err(Error::io)?;
3133

32-
letmut buf =[0];
33-
stream.read_exact(&mut buf).await.map_err(Error::io)?;
34+
letmut buf =[0];
35+
stream.read_exact(&mut buf).await.map_err(Error::io)?;
3436

35-
if buf[0] !=b'S'{
36-
ifSslMode::Require == mode{
37-
returnErr(Error::tls("server does not support TLS".into()));
38-
}else{
39-
returnOk(MaybeTlsStream::Raw(stream));
37+
if buf[0] !=b'S'{
38+
ifSslMode::Require == mode{
39+
returnErr(Error::tls("server does not support TLS".into()));
40+
}else{
41+
returnOk(MaybeTlsStream::Raw(stream));
42+
}
4043
}
4144
}
4245

‎tokio-postgres/tests/test/parse.rs‎

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
use std::time::Duration;
2-
use tokio_postgres::config::{Config,TargetSessionAttrs};
2+
use tokio_postgres::config::{Config,SslNegotiation,TargetSessionAttrs};
33

44
fncheck(s:&str,config:&Config){
55
assert_eq!(s.parse::<Config>().expect(s),*config,"`{}`", s);
@@ -42,6 +42,10 @@ fn settings() {
4242
.keepalives_idle(Duration::from_secs(30))
4343
.target_session_attrs(TargetSessionAttrs::ReadOnly),
4444
);
45+
check(
46+
"sslnegotiation=direct",
47+
Config::new().ssl_negotiation(SslNegotiation::Direct),
48+
);
4549
}
4650

4751
#[test]

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp