@@ -3,11 +3,44 @@ use std::{collections::HashMap, path::PathBuf};
3
3
use color_eyre:: eyre:: { self , Result } ;
4
4
use crossterm:: event:: { KeyCode , KeyEvent , KeyModifiers } ;
5
5
use derive_deref:: { Deref , DerefMut } ;
6
+ use percent_encoding:: { utf8_percent_encode, AsciiSet , CONTROLS } ;
6
7
use ratatui:: style:: { Color , Modifier , Style } ;
7
8
use serde:: { de:: Deserializer , Deserialize } ;
8
9
9
10
use crate :: { action:: Action , cli:: Driver , focus:: Focus , keyring:: Password } ;
10
11
12
+ // percent encoding for passwords in connection strings
13
+ const FRAGMENT : & AsciiSet = & CONTROLS
14
+ . add ( b' ' )
15
+ . add ( b'"' )
16
+ . add ( b'<' )
17
+ . add ( b'>' )
18
+ . add ( b'`' )
19
+ . add ( b'#' )
20
+ . add ( b'{' )
21
+ . add ( b'}' )
22
+ . add ( b'|' )
23
+ . add ( b'^' )
24
+ . add ( b'\\' )
25
+ . add ( b'[' )
26
+ . add ( b']' )
27
+ . add ( b'$' )
28
+ . add ( b'&' )
29
+ . add ( b'(' )
30
+ . add ( b')' )
31
+ . add ( b':' )
32
+ . add ( b';' )
33
+ . add ( b'=' )
34
+ . add ( b'?' )
35
+ . add ( b'@' )
36
+ . add ( b'!' )
37
+ . add ( b'~' )
38
+ . add ( b'\'' )
39
+ . add ( b'*' )
40
+ . add ( b'+' )
41
+ . add ( b',' )
42
+ . add ( b'/' ) ;
43
+
11
44
const CONFIG : & str = include_str ! ( "../.config/rainfrog_config.toml" ) ;
12
45
13
46
#[ derive( Clone , Debug , Deserialize , Default ) ]
@@ -65,17 +98,13 @@ pub struct Config {
65
98
66
99
impl StructuredConnection {
67
100
pub fn connection_string ( & self , driver : Driver , password : Password ) -> Result < String > {
101
+ let encoded_password = utf8_percent_encode ( password. as_ref ( ) , FRAGMENT ) ;
68
102
match driver {
69
- Driver :: Postgres => Ok ( format ! (
70
- "postgresql://{}:{}@{}:{}/{}" ,
71
- self . username,
72
- password. as_ref( ) ,
73
- self . host,
74
- self . port,
75
- self . database
76
- ) ) ,
103
+ Driver :: Postgres => {
104
+ Ok ( format ! ( "postgresql://{}:{}@{}:{}/{}" , self . username, encoded_password, self . host, self . port, self . database) )
105
+ } ,
77
106
Driver :: MySql => {
78
- Ok ( format ! ( "mysql://{}:{}@{}:{}/{}" , self . username, password . as_ref ( ) , self . host, self . port, self . database) )
107
+ Ok ( format ! ( "mysql://{}:{}@{}:{}/{}" , self . username, encoded_password , self . host, self . port, self . database) )
79
108
} ,
80
109
Driver :: Sqlite => Err ( eyre:: Report :: msg ( "Sqlite only supports raw connection strings" ) ) ,
81
110
}
0 commit comments