前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >如何保护PostgreSQL免受攻击

如何保护PostgreSQL免受攻击

原创
作者头像
独钓寒江雪_Ly
发布2018-08-02 11:07:54
1.3K0
发布2018-08-02 11:07:54
举报

介绍

服务器刚搭建,流量少,没有任何对黑客有价值的东西,你可能就会忽视相关的安全问题。但是,许多漏洞攻击都是自动化的,专门用于查找你服务中的BUG。这些服务器主要目的就是攻击,与你服务器中的数据并无多大关系。

在本教程中,我们将展示如何通过允许远程连接来缓解特定风险。虽然这是关键的第一步,但由于服务器可能会以其他方式受到威胁,我们还建议您采取其他措施来保护您的数据,如附加安全注意事项中所述

背景

要了解我们的具体风险,请将服务器想象为商店。如果服务器端口打开,这有点像打开霓虹灯的“打开”标志。它使服务器本身在网络上可见,自动脚本可以在网络上找到它。

我们可以将每个端口视为进入商店的方式,如门或窗户。根据正在端口的状态,这些入口可能是打开,关闭或损坏的,但是在公网上你的门窗是可以被尝试攻击的。脚本可能配置为尝试使用默认密码登录,密码未被更改。黑客脚本可能会尝试默认密码访问你的服务器。无论脚本尝试什么,如果它能够找到一个弱点并利用它,那么入侵者就可以攻击你,并且可以开始做危害服务器的不良行为。

在本教程中,我们将重点关注PostgreSQL数据库的安全问题。保护数据库本身或传输或存储的数据。

前期准备

在本教程中,我们将使用两个Ubuntu安装程序,一个用于数据库主机,另一个用作远程连接到主机的客户端。没有服务器的同学可以在这里购买,不过我个人更推荐您使用免费的腾讯云开发者实验室进行试验,学会安装后在购买服务器

安装PostgreSQL数据库的Ubuntu 16.04主机:

如果尚未安装PostgreSQL,可以使用以下命令安装:

代码语言:javascript
复制
sudo apt-get update
sudo apt-get install postgresql postgresql-contrib

Ubuntu 16.04客户端机器:

为了演示和测试允许远程连接,我们将使用PostgreSQL客户端psql。要安装它,请使用以下命令:

代码语言:javascript
复制
sudo apt-get update
sudo apt-get install postgresql-client

当这些前期准备完成后,您就可以继续下一步了。

了解默认配置

从Ubuntu软件包安装PostgreSQL时,默认情况下只能监听localhost。该默认可以通过配置在postgresql.conf文件中的listen_addresses修改,但默认阻止服务器公共接口上自动监听。

代码语言:javascript
复制
# Put your actual configuration here
# ----------------------------------
#
# If you want to allow non-local connections, you need to add more
# "host" records.  In that case you will also need to make PostgreSQL
# listen on a non-local interface via the listen_addresses
# configuration parameter, or via the -i or -h command line switches.
​
# DO NOT DISABLE!
# If you change this first entry you will need to make sure that the
# database superuser can access the database using some other method.
# Noninteractive access to all databases is required during automatic
# maintenance (custom daily cronjobs, replication, and similar tasks).
#
# Database administrative login by Unix domain socket
local   all             postgres                                peer
​
# TYPE  DATABASE        USER            ADDRESS                 METHOD
​
# "local" is for Unix domain socket connections only
local   all             all                                     peer
# IPv4 local connections:
host    all             all             127.0.0.1/32            md5
# IPv6 local connections:
host    all             all             ::1/128                 md5

如果您需要从远程主机进行连接,我们将介绍如何覆盖默认值以及在下一节中可以采取的保护服务器的即时步骤。

配置远程连接

对于生产设置,理想情况下,在开始处理敏感数据之前我们将使用SSL传输来保护PostgreSQL流量加密,在外部防火墙后保护。我们可以采取一些简单点的步骤,即在我们的数据库服务器上启用防火墙并限制对需要它的主机的访问。

第一步、添加用户和数据库

我们首先添加一个用户和数据库,以便测试。为此,我们将使用PostgreSQL客户端psql作为管理用户postgres进行连接。通过传递-i选项我们将运行postgres用户登录shell,这可确保我们从.profile登录的资源加载选项。 -u意思是使用postgres用户:

代码语言:javascript
复制
sudo -i -u postgres psql

接下来,我们将使用密码创建用户。请务必使用安全密码代替下面的示例:

代码语言:javascript
复制
CREATE USER sammy WITH PASSWORD 'password';

成功创建用户后,我们应该收到以下输出:

代码语言:javascript
复制
CREATE ROLE

接下来,我们将创建一个数据库并授予对新用户的完全访问权限。我们仅授予用户应具有的访问权限,因此根据用例,可能更适合限制用户的访问权限。

代码语言:javascript
复制
CREATE DATABASE sammydb OWNER sammy;

成功创建数据库后,我们应该收到确认:

代码语言:javascript
复制
CREATE DATABASE

现在,我们已经创建了一个用户和数据库,我们将退出shell

代码语言:javascript
复制
\q

按Enter后,我们将处于命令提示符并准备继续。

第二步、配置UFW

在我们开始配置之前,让我们验证UFW的状态,如果您使用的是腾讯云的CVM服务器,您可以直接在腾讯云控制台中的安全组进行设置。:

代码语言:javascript
复制
sudo ufw status

注意:如果输出指示防火墙是inactive,我们可以使用以下命令激活它: sudo ufw enable 启用后,重新运行status命令sudo ufw status将显示当前规则。如有必要,请务必允许SSH。 sudo ufw allow OpenSSH

代码语言:javascript
复制
Status: active
​
To                         Action      From
--                         ------      ----
OpenSSH                    ALLOW       Anywhere
OpenSSH (v6)               ALLOW       Anywhere (v6)

现在我们已经检查了防火墙状态,我们将允许访问PostgreSQL端口并将其限制为我们想要允许的主机。

下面的命令将添加PostgreSQL默认端口,即5432如果您已更改该端口,请务必在下面的命令中更新它。确保您已使用需要访问的服务器的IP地址。如果需要,请重新运行此命令以添加需要访问的每个客户端IP地址:

代码语言:javascript
复制
sudo ufw allow from client_ip_address to any port 5432

要仔细检查规则,我们可以再次运行ufw status

代码语言:javascript
复制
sudo ufw status
To                         Action      From
--                         ------      ----
OpenSSH                    ALLOW       Anywhere
5432                       ALLOW       client_ip_address
OpenSSH (v6)               ALLOW       Anywhere (v6)

有了这个防火墙规则,我们现在将配置PostgreSQL来监听其公共IP地址。这需要两个设置的组合,一个用于连接主机的pg_hba.conf和一个listen_addresses的配置postgresql.conf

第三步、配置允许的主机

我们首先添加主机条目pg_hba.conf。如果您安装了不同版本的PostgreSQL,请务必在以下路径中替换它:

代码语言:javascript
复制
sudo nano /etc/postgresql/9.5/main/pg_hba.conf
代码语言:javascript
复制
# If you want to allow non-local connections, you need to add more
# "host" records.  In that case you will also need to make PostgreSQL
# listen on a non-local interface via the listen_addresses
# configuration parameter, or via the -i or -h command line switches.
host  sammydb  sammy   client_ip_address/32   md5

在保存更改之前,我们来看看下面的值,以防您想要更改某些选项:

  • host确定将使用TCP/IP连接。
  • sammydb第二列指示主机可以连接到哪个数据库。通过用逗号分隔名称可以添加多个数据库。
  • sammy表示允许进行连接的用户。与数据库列一样,可以指定多个用户,用逗号分隔。
  • address该地址指定客户端计算机地址,可能包含主机名,IP地址范围或其他特殊关键字。在上面的示例中,我们只允许客户端的单个IP地址。
  • auth-method 最后,auth-method md5表示将提供双MD5哈希密码进行身份验证。您只需提供为用户连接创建的密码即可。

对于这些和其他设置一个更完整的讨论,请参阅该PostgreSQL文档pg_hba.conf文件 。

完成后,保存并退出文件。

第四步、配置侦听地址

接下来我们将在postgresql.conf文件中设置监听地址:

代码语言:javascript
复制
sudo nano /etc/postgresql/9.5/main/postgresql.conf

找到listen_addresses行,定义您的监听地址,确保替换数据库主机的主机名或IP地址。您可能需要仔细检查您是否正在使用数据库服务器的公共IP,而不是连接客户端:

代码语言:javascript
复制
#listen_addresses = 'localhost'         # what IP address(es) to listen on;
listen_addresses = 'localhost,server_ip_address'

完成后保存并退出文件。

第五步、重启PostgreSQL

在我们重新启动PostgreSQL之前,我们的配置不会生效,所以在测试之前会这样做:

代码语言:javascript
复制
sudo systemctl restart postgresql

由于systemctl不提供反馈,我们将检查状态以确保守护程序成功重新启动:

代码语言:javascript
复制
sudo systemctl status postgresql

如果输出包含Active:active并以类似下面的内容结束,则PostgreSQL守护程序正在运行。

代码语言:javascript
复制
...
Jan 10 23:02:20 PostgreSQL systemd[1]: Started PostgreSQL RDBMS.

现在我们已经重新启动了守护进程,我们已经准备好进行测试了。

第六步、测试

让我们测试一下我们可以从客户端机器连接。为此,我们将使用psql -U来指定用户,-h指定客户端的IP地址以及-d指定数据库,因为我们已经加强了安全性,因此sammy只能连接到单个数据库。

代码语言:javascript
复制
psql -U sammy -h postgres_host_ip -d sammydb

如果一切配置正确,您应该收到以下提示:

代码语言:javascript
复制
Password for user sammy:

输入sammy在PostgreSQL设置的密码。下面表示您已成功连接:

代码语言:javascript
复制
[secondary_label]
sammydb=>

这证实我们可以通过防火墙并连接到数据库。我们现在退出:

代码语言:javascript
复制
\q

第七步、删除测试数据库和用户

一旦我们完成测试连接,回到主机上,我们可以使用以下命令删除数据库和用户。

代码语言:javascript
复制
sudo -i -u postgres psql

要删除数据库:

代码语言:javascript
复制
DROP DATABASE sammydb;

该操作由以下输出确认:

代码语言:javascript
复制
DROP DATABASE

要删除用户:

代码语言:javascript
复制
DROP USER sammy;
代码语言:javascript
复制
DROP ROLE

其他安全注意事项

本教程旨在降低允许不安全的远程连接到PostgreSQL所带来的风险,这是一种常见的情况,无意中将PostgreSQL暴露给漏洞最危险。限制对特定主机的侦听端口的访问不会解决其他重要的安全注意事项,例如如何加密传输中的数据。建议您使用腾讯云SSL证书服务再次加密你的数据流量,防止中间人窃听。

结论

在本教程中,我们通过将服务器的防火墙配置为仅允许来自需要访问的主机的连接并通过将PostgreSQL配置为仅接受来自这些主机的连接来保护我们的PostgreSQL。这可以降低某些类型攻击的风险。这只是保护数据的第一步,对于生产环境的服务器,我们建议您使用腾讯云云关系型数据库,可将您从耗时的数据库管理任务中解放出来,让您有更多时间专注于您的应用和业务。 更多Linux教程请前往腾讯云+社区学习更多知识。


参考文献:《How To Secure PostgreSQL Against Automated Attacks》

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 介绍
  • 背景
  • 前期准备
    • 安装PostgreSQL数据库的Ubuntu 16.04主机:
      • Ubuntu 16.04客户端机器:
      • 了解默认配置
      • 配置远程连接
      • 第一步、添加用户和数据库
      • 第二步、配置UFW
      • 第三步、配置允许的主机
      • 第四步、配置侦听地址
      • 第五步、重启PostgreSQL
      • 第六步、测试
      • 第七步、删除测试数据库和用户
      • 其他安全注意事项
      • 结论
      相关产品与服务
      云数据库 PostgreSQL
      腾讯云数据库 PostgreSQL(TencentDB for PostgreSQL,云 API 使用 postgres 作为简称)能够让您在云端轻松设置、操作和扩展目前功能最强大的开源数据库 PostgreSQL。腾讯云将负责绝大部分处理复杂而耗时的管理工作,如 PostgreSQL 软件安装、存储管理、高可用复制、以及为灾难恢复而进行的数据备份,让您更专注于业务程序开发。
      领券
      问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档