I was surprised how vsftpd didn't work out of the box to support authentication without unix system account. It took me 2 days to research and did trial and error before I could make it work. Here is the result.
system: debian
# apt-get install libpam-pwdfile
# mkdir /etc/vsftpd
# cd /etc/vsftpd
# htpasswd -c passwd_ftp a_sample_website
Here I assume that the root directory of your virtual host is /vhdocs/a_sample_website/.
# cd /etc/pam.d
# vi vsftpd
Make sure it looks exactly like this:
# Standard behaviour for ftpd(8).
auth required pam_listfile.so item=user sense=deny file=/etc/ftpusers onerr=succeed
# Note: vsftpd handles anonymous logins on its own. Do not enable
# pam_ftp.so.
# Standard blurb.
#@include common-account
#@include common-session
#@include common-auth
#auth required pam_shells.so
# Customized login using htpasswd file
auth required pam_pwdfile.so pwdfile /etc/vsftpd/passwd_ftp
account required pam_permit.so
Then edit vsftpd's config file:
# vi /etc/vsftpd.conf
It is a long config file. I will tell you only required lines:
write_enable=YES
local_umask=022
chroot_local_user=YES
# addtitional settings by chaitat
virtual_use_local_privs=YES
connect_from_port_20=YES
guest_enable=YES
guest_username=ftp
user_sub_token=$USER
local_root=/vhdocs/$USER
hide_ids=YES
Restart vsftpd:
# /etc/init.d/vsftpd restart
Modify files' owner:
# chown -R ftp.nogroup /vhdocs/a_sample_website
--
unsigned_nerd