SFTP con chroot a seconda della chiave pubblica di connessione dell'utente


9

Voglio costruire un server (con Debian o FreeBSD) che riceva i backup da diversi client tramite sshfs. Ogni client dovrebbe essere in grado di leggere e scrivere i propri dati di backup, ma non i dati di nessuno degli altri client.

Ho avuto la seguente idea: ogni client si connette tramite la chiave pubblica auth a backup@backupserver.local. Il backup dell'utente ha un file speciale autorizzato_keys, come questo:

command="internal-sftp" chroot="/backup/client-1/data" ssh-rsa (key1)
command="internal-sftp" chroot="/backup/client-2/data" ssh-rsa (key2)
command="internal-sftp" chroot="/backup/client-3/data" ssh-rsa (key3)
etc...

Il vantaggio sarebbe che non avrei bisogno di usare un utente separato per ogni client e potrei facilmente generare automaticamente il file authorized_keys con uno script.

C'è solo un problema: il chroot=...non funziona. Il file authorized_keys di OpenSSH non sembra avere un equivalente per ChrootDirectory (che funziona in / etc / ssh / sshd_config, a livello globale o in un blocco Match User).

Esiste un modo ragionevolmente semplice per ottenere ciò che voglio usando OpenSSH? Forse usando la command=...direttiva in modo intelligente? In alternativa, ci sono altri server SFTP che possono fare quello che voglio?

EDIT : Per rendere più chiaro ciò che voglio ottenere: voglio che diversi client siano in grado di archiviare i file sul mio server. Ogni client non dovrebbe essere in grado di vedere i file di nessun altro client. E non voglio sporcare il mio server con dozzine di account utente, quindi vorrei una soluzione facilmente gestibile per i client di condividere un account utente e non avere ancora accesso ai file di ciascuno.

Risposte:


5

In alternativa, ci sono altri server SFTP che possono fare quello che voglio?

sì, puoi usare proftpd

Preparare l'ambiente utente. Con ProFTPD non è necessario fornire all'utente una shell valida.

# useradd -m -d /vhosts/backup/user1/ -s /sbin/nologin user1
# passwd --lock user1
Locking password for user user1.
passwd: Success

# mkdir /vhosts/backup/user1/.sftp/
# touch /vhosts/backup/user1/.sftp/authorized_keys

# chown -R user1:user1 /vhosts/backup/user1/
# chmod -R 700 /vhosts/backup/user1/

Per utilizzare le chiavi pubbliche OpenSSH in un SFTPAuthorizedUserKeys, è necessario convertirle nel formato RFC4716. Puoi farlo con lo strumento ssh-keygen:

# ssh-keygen -e -f user1.public.key > /vhosts/backup/user1/.sftp/authorized_keys

Configura ProFTPD

ServerName "ProFTPD Default Installation"
ServerType standalone
DefaultServer off

LoadModule mod_tls.c
LoadModule mod_sftp.c
LoadModule mod_rewrite.c

TLSProtocol TLSv1 TLSv1.1 TLSv1.2

# Disable default ftp server
Port 0

UseReverseDNS off
IdentLookups off

# Umask 022 is a good standard umask to prevent new dirs and files
# from being group and world writable.
Umask 022

# PersistentPasswd causes problems with NIS/LDAP.
PersistentPasswd off

MaxInstances 30

# Set the user and group under which the server will run.
User nobody
Group nobody

# Normally, we want files to be overwriteable.
AllowOverwrite                  on

TimesGMT off
SetEnv TZ :/etc/localtime

<VirtualHost sftp.example.net>
    ServerName "SFTP: Backup server."
    DefaultRoot ~
    Umask 002
    Port 2121

    RootRevoke on

    SFTPEngine on
    SFTPLog /var/log/proftpd/sftp.log

    SFTPHostKey /etc/ssh/ssh_host_rsa_key
    SFTPHostKey /etc/ssh/ssh_host_dsa_key
    SFTPDHParamFile /etc/pki/proftpd/dhparam_2048.pem
    SFTPAuthorizedUserKeys file:~/.sftp/authorized_keys

    SFTPCompression delayed
    SFTPAuthMethods publickey
</VirtualHost>

<Global>
    RequireValidShell off
    AllowOverwrite yes

    DenyFilter \*.*/

    <Limit SITE_CHMOD>
        DenyAll
    </Limit>
</Global>

LogFormat default "%h %l %u %t \"%r\" %s %b"
LogFormat auth    "%v [%P] %h %t \"%r\" %s"
ExtendedLog /var/log/proftpd/access.log read,write

Crea parametri di gruppo DH (Diffie-Hellman).

# openssl dhparam -out /etc/pki/proftpd/dhparam_2048.pem 2048

Configura qualsiasi client SFTP. Ho usato FileZilla

Impostazioni del server SFTP FileZilla

Se si esegue ProFPTD in modalità debug

# proftpd -n -d 3 

Nella console vedrai qualcosa di simile al seguente

2016-02-21 22:12:48,275 sftp.example.net proftpd[50511]: using PCRE 7.8 2008-09-05
2016-02-21 22:12:48,279 sftp.example.net proftpd[50511]: mod_sftp/0.9.9: using OpenSSL 1.0.1e-fips 11 Feb 2013
2016-02-21 22:12:48,462 sftp.example.net proftpd[50511] sftp.example.net: set core resource limits for daemon
2016-02-21 22:12:48,462 sftp.example.net proftpd[50511] sftp.example.net: ProFTPD 1.3.5a (maint) (built Sun Feb 21 2016 21:22:00 UTC) standalone mode STARTUP
2016-02-21 22:12:59,780 sftp.example.net proftpd[50512] sftp.example.net (192.168.1.2[192.168.1.2]): mod_cap/1.1: adding CAP_SETUID and CAP_SETGID capabilities
2016-02-21 22:12:59,780 sftp.example.net proftpd[50512] sftp.example.net (192.168.1.2[192.168.1.2]): SSH2 session opened.
2016-02-21 22:12:59,863 sftp.example.net proftpd[50512] sftp.example.net (192.168.1.2[192.168.1.2]): Preparing to chroot to directory '/vhosts/backup/user1'
2016-02-21 22:12:59,863 sftp.example.net proftpd[50512] sftp.example.net (192.168.1.2[192.168.1.2]): Environment successfully chroot()ed
2016-02-21 22:12:59,863 sftp.example.net proftpd[50512] sftp.example.net (192.168.1.2[192.168.1.2]): USER user1: Login successful

E le seguenti righe in /var/log/sftp.log

2016-02-21 22:12:48,735 mod_sftp/0.9.9[50309]: sending acceptable userauth methods: publickey
2016-02-21 22:12:48,735 mod_sftp/0.9.9[50309]: public key MD5 fingerprint: c2:2f:a3:93:59:5d:e4:38:99:4b:fd:b1:6e:fc:54:6c
2016-02-21 22:12:48,735 mod_sftp/0.9.9[50309]: sending publickey OK
2016-02-21 22:12:59,789 mod_sftp/0.9.9[50309]: public key MD5 fingerprint: c2:2f:a3:93:59:5d:e4:38:99:4b:fd:b1:6e:fc:54:6c
2016-02-21 22:12:59,790 mod_sftp/0.9.9[50309]: sending userauth success
2016-02-21 22:12:59,790 mod_sftp/0.9.9[50309]: user 'user1' authenticated via 'publickey' method

PS

Il percorso configurato per un file contenente chiavi autorizzate ( SFTPAuthorizedUserKeys ) può utilizzare la variabile % u , che verrà interpolata con il nome dell'utente da autenticare. Questa funzione supporta la disponibilità di file per utente di chiavi autorizzate che risiedono in una posizione centrale, anziché richiedere (o consentire) agli utenti di gestire le proprie chiavi autorizzate. Per esempio:

SFTPAuthorizedUserKeys file:/etc/sftp/authorized_keys/%u

Voglio che diversi client siano in grado di archiviare i file sul mio server. Ogni client non dovrebbe essere in grado di vedere i file di nessun altro client. E non voglio sporcare il mio server con dozzine di account utente, quindi vorrei una soluzione facilmente gestibile per i client di condividere un account utente e non avere ancora accesso ai file di ciascuno.

con ProFTPD è anche possibile. Hai solo bisogno di modificare leggermente la mia configurazione iniziale

<VirtualHost sftp.example.net>
    ...   
    SFTPAuthorizedUserKeys file:/etc/proftpd/sftp_authorized_keys
    AuthUserFile /etc/proftpd/sftp_users.passwd

    CreateHome on 0700 dirmode 0700 uid 99 gid 99

    RewriteHome on
    RewriteEngine on
    RewriteLog /var/log/proftpd/rewrite.log
    RewriteCondition %m REWRITE_HOME
    RewriteRule (.*) /vhosts/backup/%u
</VirtualHost>

E crea un account virtuale

# ftpasswd --passwd --file /etc/proftpd/sftp_users.passwd --sha512 --gid 99 --uid 99 --shell /sbin/nologin --name user1 --home /vhosts/backup

È tutto. Per ogni account aggiuntivo tutto ciò che serve è aggiungere la sua chiave pubblica a / etc / proftpd / sftp_authorized_keys

Nota: il file deve contenere una nuova riga alla fine! È importante.


Grazie per la tua risposta dettagliata. Tuttavia, non vedo come questo mi aiuterebbe a raggiungere il mio obiettivo principale di utilizzare un solo account utente per molti client che non dovrebbero essere in grado di vedere i file di ciascuno. (Ed essere facilmente gestibile da una sceneggiatura.) Leggendo di nuovo la mia domanda originale, ammetto che potrebbe non essere stato del tutto ovvio ciò che volevo ottenere. Scusa per quella cosa.
Xykon42,

Ho aggiornato la risposta
ALex_hha il

1
Bene, con una piccola modifica, questo funziona davvero bene, grazie! Per assicurarsi che gli utenti non possano accedere ai file di altri utenti indovinando il loro nome utente (o per inondare il mio server abusando della funzione CreateHome), il file authorized_keys deve essere specifico dell'utente, come /foo/authorized_keys.d/%u.
Xykon42

6

il chroot=...non funziona.

No, non c'è nulla di simile nella pagina di manuale per sshd, che descrive il formato del authorized_keysfile.

Se inserissi chroot command=, non saresti in grado di usarlo internal-sftp, perché è una sostituzione della chiamata di funzione interna all'interno sshd.

Modo consigliato è impostare più utenti, se è necessaria la separazione. È inoltre possibile utilizzare argomenti per internal-sftp, se non è necessaria una separazione rigorosa (ad esempio solo directory di lavoro diverse), ad esempio

command="internal-sftp -d /backup/client-1/data" ssh-rsa (key1)

È anche possibile limitare la quantità di richieste utilizzando l' -Popzione come nella pagina di manuale per sftp-server.


0

Nel frattempo, mi è venuta in mente un'altra soluzione semplice che funziona bene, almeno nel mio caso d'uso:

Ogni client si connette al server con lo stesso account utente e possibilmente anche la stessa chiave (non importa). OpenSSH esegue il chroot in una directory che ha la seguente struttura:

d--x--x---   dark-folder
drwxr-x---   |- verylongrandomfoldername1
drwxr-x---   |- verylongrandomfoldername2
drwxr-x---   `- ...

Insieme al comando di backup, il server comunica al client il nome della cartella in cui inserire i propri file. I nomi delle cartelle sono stringhe casuali a 64 byte che sono praticamente indiscutibili, quindi ogni client può davvero accedere alla propria cartella, anche se gli altri sono "da qualche parte là fuori al buio".

la modalità d - x - x-- su dark-folder assicura che ogni client possa entrare nella cartella (e nelle cartelle sottostanti), ma non può elencarne il contenuto o creare nuove voci.

Le sottocartelle vengono create dal processo del server di backup e la connessione tra client e cartella viene archiviata (tra le altre cose) in un database sqlite.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.