sftp: allow cert based auth via optional pubkey

This commit is contained in:
Stephen Harris 2020-09-24 14:51:35 -04:00
parent 433b73a5a8
commit f11255a801
2 changed files with 52 additions and 2 deletions

View File

@ -82,6 +82,9 @@ func init() {
Only PEM encrypted key files (old OpenSSH format) are supported. Encrypted keys
in the new OpenSSH format can't be used.`,
IsPassword: true,
}, {
Name: "pubkey_file",
Help: "Optional path to public key file; set this if you have a signed certificate you want to use for authentication." + env.ShellExpandHelp,
}, {
Name: "key_use_agent",
Help: `When set forces the usage of the ssh-agent.
@ -190,6 +193,7 @@ type Options struct {
KeyPem string `config:"key_pem"`
KeyFile string `config:"key_file"`
KeyFilePass string `config:"key_file_pass"`
PubKeyFile string `config:"pubkey_file"`
KeyUseAgent bool `config:"key_use_agent"`
UseInsecureCipher bool `config:"use_insecure_cipher"`
DisableHashCheck bool `config:"disable_hashcheck"`
@ -438,6 +442,7 @@ func NewFs(name, root string, m configmap.Mapper) (fs.Fs, error) {
}
keyFile := env.ShellExpand(opt.KeyFile)
pubkeyFile := env.ShellExpand(opt.PubKeyFile)
//keyPem := env.ShellExpand(opt.KeyPem)
// Add ssh agent-auth if no password or file or key PEM specified
if (opt.Pass == "" && keyFile == "" && !opt.AskPassword && opt.KeyPem == "") || opt.KeyUseAgent {
@ -507,7 +512,29 @@ func NewFs(name, root string, m configmap.Mapper) (fs.Fs, error) {
if err != nil {
return nil, errors.Wrap(err, "failed to parse private key file")
}
sshConfig.Auth = append(sshConfig.Auth, ssh.PublicKeys(signer))
// If a public key has been specified then use that
if pubkeyFile != "" {
certfile, err := ioutil.ReadFile(pubkeyFile)
if err != nil {
return nil, errors.Wrap(err, "unable to read cert file")
}
pk, _, _, _, err := ssh.ParseAuthorizedKey(certfile)
if err != nil {
return nil, errors.Wrap(err, "unable to parse cert file")
}
// And the signer for this, which includes the private key signer
// This is what we'll pass to the ssh client.
pubsigner, err := ssh.NewCertSigner(pk.(*ssh.Certificate), signer)
if err != nil {
return nil, errors.Wrap(err, "error generating cert signer")
}
sshConfig.Auth = append(sshConfig.Auth, ssh.PublicKeys(pubsigner))
} else {
sshConfig.Auth = append(sshConfig.Auth, ssh.PublicKeys(signer))
}
}
// Auth from password if specified

View File

@ -102,7 +102,7 @@ excess files in the directory.
The SFTP remote supports three authentication methods:
* Password
* Key file
* Key file, including certificate signed keys
* ssh-agent
Key files should be PEM-encoded private key files. For instance `/home/$USER/.ssh/id_rsa`.
@ -128,6 +128,17 @@ Using an ssh-agent is the only way to load encrypted OpenSSH keys at the moment.
If you set the `--sftp-ask-password` option, rclone will prompt for a
password when needed and no password has been configured.
If you have a certificate then you can provide the path to the public key that contains the certificate. For example:
```
[remote]
type = sftp
host = example.com
user = sftpuser
key_file = ~/id_rsa
pubkey_file = ~/id_rsa-cert.pub
````
### ssh-agent on macOS ###
Note that there seem to be various problems with using an ssh-agent on
@ -247,6 +258,18 @@ when the ssh-agent contains many keys.
- Type: bool
- Default: false
#### --sftp-pubkey-file
Path to public key file, set if you want to use certificate based authentication
Leading `~` will be expanded in the file name as will environment variables such as `${RCLONE_CONFIG_DIR}`.
- Config: pubkey_file
- Env Var: RCLONE_SFTP_PUBKEY_FILE
- Type: string
- Default: ""
#### --sftp-use-insecure-cipher
Enable the use of insecure ciphers and key exchange methods.