mirror of
https://github.com/mickael-kerjean/filestash
synced 2025-12-07 17:02:29 +01:00
feature (plg_backend_ftp): handle various connection strategy
This commit is contained in:
parent
1129e76ad3
commit
f5df1445d2
1 changed files with 82 additions and 29 deletions
|
|
@ -80,43 +80,96 @@ func (f Ftp) Init(params map[string]string, app *App) (IBackend, error) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
configWithoutTLS := goftp.Config{
|
connectStrategy := []string{"ftp", "ftps::implicit", "ftps::explicit"}
|
||||||
User: params["username"],
|
if strings.HasPrefix(params["hostname"], "ftp://") {
|
||||||
Password: params["password"],
|
connectStrategy = []string{"ftp"}
|
||||||
ConnectionsPerHost: conn,
|
params["hostname"] = strings.TrimPrefix(params["hostname"], "ftp://")
|
||||||
Timeout: 60 * time.Second,
|
} else if strings.HasPrefix(params["hostname"], "ftps://") {
|
||||||
|
connectStrategy = []string{"ftps::implicit", "ftps::explicit"}
|
||||||
|
params["hostname"] = strings.TrimPrefix(params["hostname"], "ftps://")
|
||||||
}
|
}
|
||||||
configWithTLS := configWithoutTLS
|
|
||||||
configWithTLS.TLSConfig = &tls.Config{
|
|
||||||
InsecureSkipVerify: true,
|
|
||||||
ClientSessionCache: tls.NewLRUClientSessionCache(32),
|
|
||||||
}
|
|
||||||
configWithTLS.TLSMode = goftp.TLSExplicit
|
|
||||||
|
|
||||||
var backend *Ftp = nil
|
var backend *Ftp = nil
|
||||||
|
hostname := fmt.Sprintf("%s:%s", params["hostname"], params["port"])
|
||||||
// Attempt to connect using FTPS
|
cfgBuilder := func(timeout time.Duration, withTLS bool) goftp.Config {
|
||||||
if client, err := goftp.DialConfig(configWithTLS, fmt.Sprintf("%s:%s", strings.TrimPrefix(params["hostname"], "ftps://"), params["port"])); err == nil {
|
cfg := goftp.Config{
|
||||||
if _, err := client.ReadDir("/"); err != nil {
|
User: params["username"],
|
||||||
|
Password: params["password"],
|
||||||
|
ConnectionsPerHost: conn,
|
||||||
|
Timeout: timeout * time.Second,
|
||||||
|
}
|
||||||
|
cfg.Timeout = timeout
|
||||||
|
if withTLS {
|
||||||
|
cfg.TLSConfig = &tls.Config{
|
||||||
|
InsecureSkipVerify: true,
|
||||||
|
ClientSessionCache: tls.NewLRUClientSessionCache(0),
|
||||||
|
SessionTicketsDisabled: false,
|
||||||
|
ServerName: hostname,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return cfg
|
||||||
|
}
|
||||||
|
for i := 0; i < len(connectStrategy); i++ {
|
||||||
|
if connectStrategy[i] == "ftp" {
|
||||||
|
client, err := goftp.DialConfig(cfgBuilder(5*time.Second, false), hostname)
|
||||||
|
if err != nil {
|
||||||
|
Log.Debug("plg_backend_ftp::ftp dial %s", err.Error())
|
||||||
|
continue
|
||||||
|
} else if _, err := client.ReadDir("/"); err != nil {
|
||||||
|
client.Close()
|
||||||
|
Log.Debug("plg_backend_ftp::ftp verify %s", err.Error())
|
||||||
|
continue
|
||||||
|
}
|
||||||
client.Close()
|
client.Close()
|
||||||
} else {
|
client, err = goftp.DialConfig(cfgBuilder(60*time.Second, false), hostname)
|
||||||
|
if err != nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
params["mode"] = connectStrategy[i]
|
||||||
backend = &Ftp{client, params, nil}
|
backend = &Ftp{client, params, nil}
|
||||||
}
|
break
|
||||||
}
|
} else if connectStrategy[i] == "ftps::implicit" {
|
||||||
|
cfg := cfgBuilder(60*time.Second, true)
|
||||||
// Attempt to create an FTP connection if FTPS isn't available
|
cfg.TLSMode = goftp.TLSImplicit
|
||||||
if backend == nil {
|
client, err := goftp.DialConfig(cfg, hostname)
|
||||||
client, err := goftp.DialConfig(configWithoutTLS, fmt.Sprintf("%s:%s", strings.TrimPrefix(params["hostname"], "ftp://"), params["port"]))
|
if err != nil {
|
||||||
if err != nil {
|
Log.Debug("plg_backend_ftp::ftps::implicit dial %s", err.Error())
|
||||||
return backend, err
|
continue
|
||||||
}
|
} else if _, err := client.ReadDir("/"); err != nil {
|
||||||
if _, err := client.ReadDir("/"); err != nil {
|
Log.Debug("plg_backend_ftp::ftps::implicit verify %s", err.Error())
|
||||||
|
client.Close()
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
params["mode"] = connectStrategy[i]
|
||||||
|
backend = &Ftp{client, params, nil}
|
||||||
|
break
|
||||||
|
} else if connectStrategy[i] == "ftps::explicit" {
|
||||||
|
cfg := cfgBuilder(5*time.Second, true)
|
||||||
|
cfg.TLSMode = goftp.TLSExplicit
|
||||||
|
client, err := goftp.DialConfig(cfg, hostname)
|
||||||
|
if err != nil {
|
||||||
|
Log.Debug("plg_backend_ftp::ftps::explicit dial '%s'", err.Error())
|
||||||
|
continue
|
||||||
|
} else if _, err := client.ReadDir("/"); err != nil {
|
||||||
|
Log.Debug("plg_backend_ftp::ftps::explicit verify %s", err.Error())
|
||||||
|
client.Close()
|
||||||
|
continue
|
||||||
|
}
|
||||||
client.Close()
|
client.Close()
|
||||||
return backend, ErrAuthenticationFailed
|
cfg = cfgBuilder(60*time.Second, true)
|
||||||
|
cfg.TLSMode = goftp.TLSExplicit
|
||||||
|
client, err = goftp.DialConfig(cfg, hostname)
|
||||||
|
if err != nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
params["mode"] = connectStrategy[i]
|
||||||
|
backend = &Ftp{client, params, nil}
|
||||||
|
break
|
||||||
}
|
}
|
||||||
backend = &Ftp{client, params, nil}
|
|
||||||
}
|
}
|
||||||
|
if backend == nil {
|
||||||
|
return nil, ErrAuthenticationFailed
|
||||||
|
}
|
||||||
backend.wg = new(sync.WaitGroup)
|
backend.wg = new(sync.WaitGroup)
|
||||||
backend.wg.Add(1)
|
backend.wg.Add(1)
|
||||||
go func() {
|
go func() {
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue