2025-03-28 19:57:44 +01:00

96 lines
2.4 KiB
Go

package kopia
import (
"backea/internal/logging"
"context"
"fmt"
"os"
"os/exec"
"path/filepath"
)
// SFTPProvider implements the Provider interface for SFTP remote storage
type SFTPProvider struct {
Host string
BasePath string
Username string
KeyFile string
logger *logging.Logger
}
// NewSFTPProvider creates a new SFTP provider
func NewSFTPProvider(host, basePath, username, keyFile string) *SFTPProvider {
return &SFTPProvider{
Host: host,
BasePath: basePath,
Username: username,
KeyFile: keyFile,
logger: logging.GetLogger(),
}
}
func (p *SFTPProvider) Connect(ctx context.Context, serviceName string, password string, configPath string) error {
repoPath := fmt.Sprintf("%s/%s", p.BasePath, serviceName)
knownHostsPath := filepath.Join(os.Getenv("HOME"), ".ssh", "known_hosts")
connectCmd := exec.CommandContext(
ctx,
"kopia",
"--config-file", configPath,
"repository", "connect", "sftp",
"--path", repoPath,
"--host", p.Host,
"--username", p.Username,
"--keyfile", p.KeyFile,
"--known-hosts", knownHostsPath,
"--password", password,
)
err := connectCmd.Run()
if err != nil {
p.logger.Info("Creating new SFTP repository for %s at %s", serviceName, repoPath)
createCmd := exec.CommandContext(
ctx,
"kopia",
"--config-file", configPath,
"repository", "create", "sftp",
"--path", repoPath,
"--host", p.Host,
"--username", p.Username,
"--keyfile", p.KeyFile,
"--known-hosts", knownHostsPath,
"--password", password,
)
createOutput, err := createCmd.CombinedOutput()
if err != nil {
return NewKopiaError(fmt.Sprintf("failed to create SFTP repository: %s", string(createOutput)), err)
}
}
return nil
}
// GetRepositoryParams returns parameters for SFTP operations
func (p *SFTPProvider) GetRepositoryParams(serviceName string) ([]string, error) {
repoPath := fmt.Sprintf("%s@%s:%s/%s", p.Username, p.Host, p.BasePath, serviceName)
knownHostsPath := filepath.Join(os.Getenv("HOME"), ".ssh", "known_hosts")
return []string{
"sftp",
"--path", repoPath,
"--keyfile", p.KeyFile,
"--known-hosts", knownHostsPath,
}, nil
}
// GetBucketName returns the path for a service
func (p *SFTPProvider) GetBucketName(serviceName string) string {
return fmt.Sprintf("%s/%s", p.BasePath, serviceName)
}
// GetProviderType returns the provider type identifier
func (p *SFTPProvider) GetProviderType() string {
return "sftp"
}