设置与Postgresql后端proftpd为验证和日志

PostgreSQL和Proftpd

所以你想要设置一个ftp服务器,你需要高级功能,你不知道在哪里转? 尝试proftpd。

第1部分:使用postgresql后端设置proftpd

本教程非常适用,我将仅覆盖proftpd,并且只能使其与Postgres一起运行。 假设对proftpd和Postgres的基本了解。 本教程将让您快速运行proftpd,并使其使用数据库,如果该数据库具有触发器,则此配置的可能性几乎是无止境的。

获得Proftpd

首先你需要proftpd,我将使用Ubuntu的Dapper; 有一个由Francesco Paolo Lovergine提供的名为“proftpd-pgsql”的元包,它将设置一个使用以下模块编译的proftpd的副本。 作为旁注,当proftpd附带mod时,conf文件是标准的proftpd样板。 我强烈建议您查看mod_sql文档,而sub-par仍然很方便 - proftpd站点上的文档很旧,使用这些文件链接到文档 。 此外,厌倦的版本,proftpd现在是1.3,虽然我将使用1.2.10 - Dapper中使用的版本

编译到这个版本的proftpd的mods如下

  mod_core.c
mod_xfer.c
mod_auth_unix.c
mod_auth_file.c
mod_auth.c
mod_ls.c
mod_log.c
mod_site.c
mod_auth_pam.c
mod_quotatab.c
mod_sql.c
mod_sql_postgres.c
mod_quotatab_sql.c
mod_ratio.c
mod_tls.c
mod_rewrite.c
mod_radius.c
mod_wrap.c
mod_quotatab_file.c
mod_delay.c
mod_readme.c
mod_ifsession.c
mod_cap.c
继续执行命令以获取proftpd-pgsql:
apt-get install proftpd-pgsql

设置权限

为了我的目的,(记住,我是宇宙的中心),我需要的是一维结构,因为组存储在不同的级别而不是unix权限。 所以所有文件都应该有静态权限 - 我只关心所有者和所有者的组。 我的计划是使proftpd默认用户ftp属于自己正确命名的组,我将要创建 - 'ftp'。 然后我打算让Postgres成为这个团体的成员,参见第2部分的推理。 我需要两个成为同一个组的成员,我需要proftpd chroot文件夹为775,所以整个组可以添加(移动)文件,我还使用用户'ftp'拥有的文件夹,组'ftp '。 我用以下脚本完成了这个。

groupadd ftp
usermod -G ftp ftp
usermod -G ftp,postgres postgres
chown ftp:ftp ./ftp_directory/
chmod 775 ./ftp_directory/

设置Postgres

现在,我们将准备好我们的sql表。 我设计利用模式,这是“ftp”的前缀。 在桌子上是为了。 我把所有的表格都放在一个ftp模式中,有一件事情值得一下,我对这个项目的权限是非常有限制的,因为我不知道mod_sql是多么的安全。 在这样做的时候,我创建了一个名为proftp的特殊用户,用于我的数据库中的proftpd(比proftpd使用更多的应用程序),该用户被限制在auth_table上进行选择,并插入到file_log表中。 我*高度*建议你采取这种政策的某种形式。 至少这样可以防止某些程度的破坏性的sql注入攻击或信息泄漏,在mod_sql代码不像我们想要的那样安全的情况下。 一个快速的google显示了mod_sql代码库以前的安全问题。 mod_sql发送到db的每个查询都附加了一个“LIMIT 1”子句,并且mod_delay也默认配置,我发现这个项目足够了。

我的sql init脚本如下。

ALTER USER proftp UNENCRYPTED PASSWORD 'dealermadeftp';
CREATE SCHEMA ftp;
GRANT USAGE ON SCHEMA ftp TO proftp;

CREATE TABLE ftp.users (
        pkid      serial      PRIMARY KEY,
        userid    text        NOT NULL UNIQUE,
        passwd    text,
        uid       int,
        gid       int,
        homedir   text,
        shell     text
);
GRANT SELECT ON ftp.users TO proftp;
INSERT INTO ftp.users ( userid, passwd ) VALUES ( 'ecarroll', 'adm1n' );
INSERT INTO ftp.users ( userid, passwd ) VALUES ( 'jgallagher', 'adm1n' );

CREATE TABLE ftp.file_log (
        pkid               serial      PRIMARY KEY,
        userid             text        REFERENCES ftp.users(userid),
        abs_path           text,
        file               text,
        dns                text,
        time_transaction   text,
        ts_in              timestamp with time zone   NOT NULL DEFAULT CURRENT_TIMESTAMP
);
GRANT INSERT ON ftp.file_log TO proftp;
GRANT UPDATE ON TABLE ftp.file_log_pkid_seq TO proftp;

连接到您的数据库,并运行:

\i script_name

或者,您可以使用send'--file script_name'作为命令行争用的psql

那些在较小的数据库(使用本教程与mysql),你可能想用varchar替换文本; 但是,由于Postgres的设计没有优势。

设置proftpd

这部分是棘手的,如果你使用1.3 - 再次这个教程是1.2.10,稍微变化。

我已将这部分添加到我的默认proftpd模板文件conf,位于/etc/proftpd.conf:

AuthOrder            mod_sql.c
SQLAuthTypes         Plaintext Empty
SQLAuthenticate      users
SQLConnectInfo       proftpd@localhost proftp dealermadeftp

SQLDefaultUID        110   # CHANGE FOR YOUR FTP USERS UID FOUND IN /etc/passwd
SQLDefaultGID        1001  # CHANGE FOR YOUR FTP USERS GID, FOUND IN /etc/groups
SQLDefaultHomedir    /home/ftp
RequireValidShell    off

SQLUserInfo          ftp.users userid passwd uid gid homedir shell

SQLNegativeCache     off
SQLLogFile           /var/log/proftpd-sql
SQLLog               STOR newfile
SQLNamedQuery        newfile FREEFORM "INSERT INTO ftp.file_log(userid,abs_path,file,dns,time_transaction) VALUES ('%U','%f','%J','%V','%T')"

# %U => userid
# %D => --Nothing,
# %f => abs_path
# %J => file
# %h => dns_remote, %V => dns_local
# %a => remote_ip, %L => local_ip
# %t => localtime
# %T => transfer_time

*模板变量被注释,仅供您自己参考。 conf的简短说明如下:

  1. 这里我们将AuthOrder设置为mod_sql.c,反过来启用mod_sql
  2. 我选择使用Plaintext密码,或者如果我没有分配一个密码,则允许使用空密码。 (我稍后会对数据库中的密码实施SHA1的触发器)
  3. 然后我将SQLAuthenticate设置为用户,我选择不为此项目使用组,如果您需要组,可以在这些表上找到更多的信息: 本网站上的文档
  4. SQLConnectInfo是“数据库@主机用户密码”格式的dsn,
  5. SQLDefaultUID,SQLDefaultGID,SQLDefaultHomedir,配置默认值,将我的大部分列留为NULL,我很少会覆盖此。
  6. RequireValidShell也被设置为关闭,如果将其设置为on,并且提供无效的shell,那么将会验证失败。
  7. SQLUserInfo对应于Postgres表,它是一个文字映射,再次是“ftp”。 指定认证表的架构
  8. SQLNegativeCache,缓存认证失败,
  9. SQLLogFile用于在配置服务器时进行详细日志记录。 当我去生产时,我将禁用
  10. SQLLog指定你想要记录的ftp操作,因为我的用户只能上传,我只记录STOR,格式为'ftpaction query_to_execute'
  11. SQLNamedQuery检查这个文档中的语法,以便更好的解释我使用的格式是'qryname FREEFORM custom_query_here',我这样做主要是因为我希望捕获很多proftpd的模板变量,还有其他更简单的语法

而已。 如果所有人都去计划,你应该开始工作。 现在当有人上传文件时,应该是这样的结果:

proftpd=# select * from ftp.file_log;
 pkid |  userid  |        abs_path        |     file      |  dns  | time_transaction |             ts_in 
------+----------+------------------------+---------------+-------+------------------+-------------------------------
    1 | ecarroll | /home/ftp/foo/testfile | /foo/testfile | AMD64 | 0.000            | 2006-06-11 20:49:12.623375-05
(1 row)

第二部分:超越“工作”

...但是*工作是不够的吧? 让我们继续回答在配置faq for proftpd中发布的以下问题:
上载后可以将文件从上传目录中旋转出来吗?

答案是肯定可以的。 我将通过一个存储过程来实现这一点,即文件被移动到正确的方式 - 即时 - 没有一个守护进程。

您将首先需要在系统上安装* un * trusted plperlu,这可以实现

apt-get install postgresql-plperl-8.1

那么你需要在数据库中安装plperlu

createlang plperlu your_database_here

接下来,我们需要创建一个快速的perl脚本触发器,这将触发每个插入到我们的ftp_log表中

CREATE OR REPLACE FUNCTION ftp_file() RETURNS TRIGGER AS $$
        use warnings;
        use Cwd;
        use File::Basename;
        use File::Spec;
        use File::Copy;
        move (
                $_TD->{new}{abs_path},
                File::Spec->catfile( '/home/ftp/', basename($_TD->{new}{file}) )
        );
        return;
$$ LANGUAGE 'plperlu' VOLATILE;

CREATE TRIGGER ftp_file
        BEFORE INSERT
        ON ftp.file_log
        FOR EACH ROW
        EXECUTE PROCEDURE ftp_file()
;

这个sql脚本的安装方式与先前的安装方式相同(用于创建表的方法)

赞(52) 打赏
未经允许不得转载:优客志 » 系统运维
分享到:

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

微信扫一扫打赏