SFTP File Transfer Logs - How?

Hi,

I want to log all file transfer activity on sftp connections.

I’ve tried to modify /etc/sshd/sshd_config like this:

Subsystem sftp /usr/lib/openssh/sftp-server -l VERBOSE -f LOCAL3

But it didn’t work.

If it possible i want to log all file activity to a separate log file like /var/log/sftp-activity.log

And inside that file i want to see login attempts, uploads, downloads, moves, deleting files, logouts etc.. All activity.

How can I achieve this?

I thought it was an interesting question and did a quick search. gave me a couple more questions

  1. does hestia do a chroot for sftp users ?
  2. did you set up the additional configuration to log chroot sftp user

this was the first and only link i took the time to look at

  1. Yes Hestia do a chroot for sftp users (atleast Additional SFTP User Accounts).

  2. I did not setup additional configuration to log chroot sftp user. (Not to break hestia setup.)

The best solution that i found but afraid to test was:

To log SFTP activity inside a chroot environment, you must create a logging socket (/dev/log) inside each user’s chroot directory.

By default, OpenSSH logs activity by writing to the global system socket at /dev/log. However, when a user is restricted to a chroot jail, that global socket becomes physically unreachable to the isolated internal-sftp process, which completely breaks standard logging.

Follow these steps to establish a dedicated logging path for chrooted users using OpenSSH and rsyslog.

1. Configure OpenSSH for SFTP Logging

Open your SSH daemon configuration file and tell the internal subsystem to register file transfer requests.

  1. Open /etc/ssh/sshd_config in your preferred text editor.

  2. Locate or add the Subsystem sftp directive and configure it to use internal-sftp with verbosity flags:

    text

    Subsystem sftp internal-sftp -f LOCAL7 -l INFO
    
    

    Kodu dikkatli kullanın.

    (Note: -f LOCAL7 routes SFTP logs to a custom syslog facility, and -l INFO captures uploads, downloads, and deletions.)

  3. Apply this tracking behavior directly inside your Match block configuration:

    text

    Match Group sftpusers
        ChrootDirectory /sftp/%u
        ForceCommand internal-sftp -f LOCAL7 -l INFO
        AllowTcpForwarding no
        PermitTTY no
    
    

    Kodu dikkatli kullanın.

2. Build the Internal Chroot Directory Structure

Because syslog demands a target endpoint within the jail, you must create a dedicated /dev folder inside every single user’s chroot directory.

Run the following commands as root (replace /sftp/username with your exact paths):

bash

sudo mkdir -p /sftp/username/dev
sudo chmod 755 /sftp/username/dev
sudo chown root:root /sftp/username /sftp/username/dev

Kodu dikkatli kullanın.

Warning: The chroot home path and its /dev directory must be owned strictly by root and cannot be writeable by the user, or OpenSSH will completely refuse the login session.

3. Route the Sockets via Rsyslog

Tell rsyslog to drop a listening socket into the chroot directory and redirect those captured logs out to an independent file.

  1. Create a dedicated configuration drop-in file at /etc/rsyslog.d/sftp.conf.

  2. Populate the file with the layout below:

    text

    # Bind a system logging socket inside the user jail
    module(load="imuxsock")
    input(type="imuxsock" Socket="/sftp/username/dev/log" CreatePath="on")
    
    # Stream the internal-sftp activity into its own destination file
    if $programname == 'internal-sftp' then /var/log/sftp.log
    & stop
    
    

    Kodu dikkatli kullanın.

    (If managing multiple chroot folders, add a new input(...) socket path assignment line for each unique user directory.)

4. Restart Services & Review Live Activity

Restart both background system daemons to finalize the logging bridge:

bash

sudo systemctl restart rsyslog
sudo systemctl restart sshd

Kodu dikkatli kullanın.

sounds like you have realized there is more to it.

I dont use sftp so cant help any further. It does look like from what I have read you need to create a socket for every user. Not sure how practical that would be or if it could be automated. Also I dont whether these changes would affect hestia.

good luck