PAM可插入身份验证是MySQL企业版(一个商业产品)中包含的扩展。要了解更多关于商业产品的信息,请参见https://www.10bet靠谱mysql.com/products/.
MySQL企业版支持一种认证方法,使MySQL服务器可以使用PAM(可插入认证模块)对MySQL用户进行认证。PAM使系统能够使用标准接口访问各种身份验证方法,例如传统的Unix密码或LDAP目录。
PAM可插入身份验证提供了以下功能:
外部身份验证:PAM身份验证使MySQL Server能够接受来自MySQL授权表之外定义的用户的连接,并使用PAM支持的方法进行身份验证。
代理用户支持:根据外部用户所属的PAM组和提供的身份验证字符串,PAM身份验证可以向MySQL返回一个不同于客户机程序传递的外部用户名的用户名。这意味着插件可以返回MySQL用户,该用户定义了外部pam认证用户应该拥有的特权。例如,名为
乔
可以连接并拥有MySQL用户的权限开发人员
.
PAM可插入身份验证已经在Linux和macOS上进行了测试。
下表显示了插件和库文件名。不同系统的文件名后缀可能不同。文件必须位于由plugin_dir
系统变量。有关安装信息,请参见安装PAM可插入身份验证.
表6.17 PAM认证的插件和库名称
插件或文件 | 插件或文件名 |
---|---|
服务器端插件 | authentication_pam |
客户端插件 | mysql_clear_password |
库文件 | authentication_pam.so |
客户端mysql_clear_password
与服务器端PAM插件通信的cleartext插件内置在libmysqlclient
客户端库,并包含在所有发行版中,包括社区发行版。在所有MySQL发行版中包含的客户端明文插件使来自任何发行版的客户端能够连接到加载了服务器端PAM插件的服务器。
以下部分提供了特定于PAM可插入身份验证的安装和使用信息:
有关MySQL中可插入身份验证的一般信息,请参见第6.2.17节,“可插入认证”.有关mysql_clear_password
插件,看到第6.4.1.4节,“客户端明文可插入认证”.代理用户信息请参见第6.2.19节“代理用户”.
本节概述MySQL和PAM如何一起对MySQL用户进行身份验证。有关显示如何设置MySQL帐户以使用特定PAM服务的示例,请参见使用PAM可插入身份验证.
客户端程序和服务器通信,客户端向服务器发送客户端用户名(默认为操作系统用户名)和密码:
客户端用户名为外部用户名。
对于使用PAM服务器端身份验证插件的帐户,对应的客户端插件为
mysql_clear_password
.这个客户端插件不执行密码哈希,其结果是客户端将密码以明文的形式发送给服务器。
服务器根据外部用户名和客户机连接的主机查找匹配的MySQL帐户。PAM插件使用MySQL Server传递给它的信息(如用户名、主机名、密码和认证字符串)。当您定义使用PAM进行身份验证的MySQL帐户时,身份验证字符串包含:
PAM服务名称,系统管理员可以使用该名称引用特定应用程序的身份验证方法。可以有多个应用程序与单个数据库服务器实例相关联,因此服务名称的选择留给SQL应用程序开发人员。
如果要使用代理,可以选择从PAM组到MySQL用户名的映射。
插件使用身份验证字符串中命名的PAM服务检查用户凭据并返回
'认证成功,用户名为
或user_name
'“验证失败”
.密码必须适合PAM服务使用的密码存储。例子:对于传统的Unix密码,该服务查找存储在
/etc/shadow
文件。对于LDAP,该服务查找存储在LDAP目录中的密码。
如果凭据检查失败,服务器将拒绝连接。
否则,认证字符串指示是否发生代理。如果字符串不包含PAM组映射,则不会发生代理。本例中MySQL用户名与外部用户名相同。
否则,将根据PAM组映射指示代理,根据映射列表中的第一个匹配组确定MySQL用户名。的意思”帕姆集团”取决于PAM服务。例子:
对于传统的Unix密码,组是在
所属
文件,可能在文件中补充了额外的PAM信息,例如/etc/security/group.conf
.对于LDAP,组是指在LDAP目录中定义的LDAP组。
如果代理用户(外部用户)具有
代理
当代理MySQL用户的权限被代理时,就会发生代理,代理用户将拥有被代理用户的权限。
本节介绍如何安装服务器端PAM认证插件。有关安装插件的一般信息,请参见第5.6.1节“安装和卸载插件”.
为了被服务器使用,插件库文件必须位于MySQL插件目录(由plugin_dir
系统变量)。如果有必要,可以通过设置的值来配置插件目录位置plugin_dir
在服务器启动。
插件库文件名为authentication_pam
.每个平台的文件名后缀不同(例如,所以
对于Unix和类Unix系统,. dll
对于Windows)。
要在服务器启动时加载插件,请使用——plugin-load-add
选项来命名包含它的库文件。使用这种插件加载方法,必须在每次服务器启动时给出该选项。例如,将这些行放在服务器中my.cnf
文件,调整所以
为您的平台添加必要的后缀:
(mysqld) plugin-load-add = authentication_pam.so
修改后my.cnf
,重新启动服务器,使新的设置生效。
或者,要在运行时加载插件,使用此语句,调整所以
为您的平台添加必要的后缀:
安装插件authentication_pam.so;
安装插件
立即加载插件,并将其注册到mysql.plugins
系统表,使服务器在以后每次正常启动时都加载它,而不需要——plugin-load-add
.
要验证插件安装,请检查INFORMATION_SCHEMA。插件
表或使用显示插件
声明(见第5.6.2节“获取服务器插件信息”).例如:
mysql> SELECT PLUGIN_NAME, PLUGIN_STATUS FROM INFORMATION_SCHEMA。PLUGIN_NAME LIKE '%pam%';+--------------------+---------------+ | PLUGIN_NAME | PLUGIN_STATUS | +--------------------+---------------+ | authentication_pam |活跃 | +--------------------+---------------+
如果插件初始化失败,请检查服务器错误日志中的诊断消息。
要将MySQL帐户与PAM插件关联,请参见使用PAM可插入身份验证.
用于卸载PAM身份验证插件的方法取决于您如何安装它:
如果您在服务器启动时使用
——plugin-load-add
选项,在没有该选项的情况下重新启动服务器。如果你在运行时使用
安装插件
语句,它将在服务器重新启动时保持安装。要卸载它,请使用卸载插件
:卸载插件authentication_pam;
本节简要介绍如何使用PAM身份验证插件从MySQL客户端程序连接到服务器。以下部分提供了如何以特定方式使用PAM身份验证的说明。假设服务器运行时启用了服务器端PAM插件,如中所述安装PAM可插入身份验证.
的PAM身份验证插件认同
一个条款创建用户
语句,使用名称authentication_pam
.例如:
创建用户用户pam AS 'auth_string”;
认证字符串指定以下类型的信息:
PAM服务名(参见MySQL用户PAM认证是如何工作的).下面讨论中的示例使用的服务名
mysql-unix
使用传统Unix密码进行身份验证mysql-ldap
进行LDAP认证。对于代理支持,PAM为PAM模块提供了一种方法,使其向服务器返回MySQL用户名,而不是客户机程序在连接到服务器时传递的外部用户名。使用认证字符串来控制从外部用户名到MySQL用户名的映射。如果希望利用代理用户功能,身份验证字符串必须包括这种映射。
例如,如果帐户使用mysql-unix
中的操作系统用户根
而且用户
PAM组到开发人员
而且data_entry
MySQL用户分别使用如下语句:
创建用户用户mysql-unix, root=developer, users=data_entry;
PAM身份验证插件的身份验证字符串语法遵循以下规则:
该字符串由一个PAM服务名组成,后面可选地跟着一个PAM组映射列表,由一个或多个关键字/值对组成,每个关键字/值对指定一个PAM组名和一个MySQL用户名:
pam_service_name(,pam_group_name=mysql_user_name)……
插件为每个使用该帐户的连接尝试解析身份验证字符串。为了减少开销,请保持字符串尽可能短。
每一个
Pair前必须加逗号。pam_group_name
=mysql_user_name
不位于双引号内的前导和尾随空格将被忽略。
非挂牌
pam_service_name
,pam_group_name
,mysql_user_name
值可以包含除等号、逗号或空格之外的任何内容。如果一个
pam_service_name
,pam_group_name
,或mysql_user_name
值用双引号括起来,引号之间的一切都是值的一部分。这是必要的,例如,如果值包含空格字符。除了双引号和反斜杠(\
).要包含任意一个字符,用反斜杠对其进行转义。
如果插件成功验证了外部用户名(客户端传递的名称),它会在认证字符串中查找PAM组映射列表,如果存在,根据外部用户所属的PAM组,使用它返回一个不同的MySQL用户名给MySQL服务器:
如果认证字符串不包含PAM组映射列表,插件将返回外部名称。
如果身份验证字符串不包含PAM组映射列表,则插件检查每一个
从左到右对列表中的值,并尝试为pam_group_name
=mysql_user_name
pam_group_name
值,并返回分配给认证用户的组的非mysql目录mysql_user_name
对于它找到的第一个匹配。如果插件没有找到任何PAM组的匹配,它将返回外部名称。如果插件不能在目录中查找组,它将忽略PAM组映射列表并返回外部名称。
以下部分描述了如何设置几个使用PAM身份验证插件的身份验证场景:
没有代理的用户。这只使用PAM检查登录名和密码。每个被允许连接到MySQL Server的外部用户都应该有一个匹配的MySQL帐户,该帐户被定义为使用PAM身份验证。的MySQL帐户
'
为了匹配外部用户,user_name
“@”host_name
'user_name
必须是外部用户名和host_name
必须与客户端连接的主机相匹配。)身份验证可以通过各种pam支持的方法执行。后面的讨论将展示如何使用传统Unix密码和LDAP中的密码对客户机凭据进行身份验证。如果不通过代理用户或PAM组进行PAM身份验证,则需要MySQL用户名与操作系统用户名相同。MySQL用户名限制在32个字符(参见第6.2.3节“授予表格”),它将PAM非代理身份验证限制为名称不超过32个字符的Unix帐户。
仅代理用户,使用PAM组映射。对于这个场景,创建一个或多个MySQL帐户,它们定义不同的特权集。(理想情况下,任何人都不应该直接使用这些账户进行连接。)然后定义一个默认用户通过PAM进行身份验证,该PAM使用某种映射方案(通常基于用户所属的外部PAM组)将所有外部用户名映射到持有特权集的少数MySQL帐户。任何连接并指定外部用户名作为客户端用户名的客户端都映射到其中一个MySQL帐户并使用其特权。讨论将展示如何使用传统的Unix密码设置这一点,但也可以使用LDAP等其他PAM方法。
这些场景可能会发生变化:
您可以允许一些用户直接登录(不需要代理),但要求其他用户通过代理帐户连接。
通过在经过PAM身份验证的帐户中使用不同的PAM服务名称,可以对某些用户使用一种PAM身份验证方法,对其他用户使用另一种方法。例如,您可以使用
mysql-unix
为一些用户提供PAM服务,以及mysql-ldap
为他人。
这些例子做了以下假设。如果您的系统设置不同,您可能需要做一些调整。
登录名和密码分别为
安东尼奥
而且antonio_password
,分别。将这些更改为与您希望进行身份验证的用户相对应。PAM配置目录为
/etc/pam.d
.PAM服务名称对应于身份验证方法(
mysql-unix
或mysql-ldap
在这个讨论中)。要使用给定的PAM服务,必须在PAM配置目录中设置具有相同名称的PAM文件(如果文件不存在,则创建该文件)。的身份验证字符串中命名PAM服务创建用户
声明用于使用该PAM服务进行身份验证的任何帐户。
PAM身份验证插件在初始化时检查是否AUTHENTICATION_PAM_LOG
环境值在服务器的启动环境中设置。如果是,该插件支持将诊断消息记录到标准输出。根据服务器的启动方式,消息可能出现在控制台或错误日志中。这些消息有助于调试插件执行身份验证时发生的与pam相关的问题。有关更多信息,请参见PAM身份验证调试.
这个身份验证场景使用PAM检查根据操作系统用户名和Unix密码定义的外部用户,而不使用代理。每个允许连接到MySQL Server的外部用户都应该有一个匹配的MySQL帐户,该帐户被定义为通过传统的Unix密码存储使用PAM身份验证。
检查传统Unix密码使用/etc/shadow
文件。有关与此文件相关的可能问题的信息,请参见PAM对Unix密码库的身份验证访问.
验证Unix身份验证是否允许使用用户名登录到操作系统
安东尼奥
和密码antonio_password
.将PAM设置为使用传统Unix密码验证MySQL连接
mysql-unix
PAM服务文件/etc/pam.d/mysql-unix
.文件内容与系统相关,因此请检查中现有的与登录相关的文件/etc/pam.d
看看他们长什么样。在Linux上,mysql-unix
文件可能看起来像这样:#%PAM-1.0 auth include password-auth account include password-auth
对于macOS,使用
登录
而不是password-auth
.在某些系统上,PAM文件格式可能不同。例如,在Ubuntu和其他基于debian的系统上,使用以下文件内容:
@include common-auth @include common-account @include common-session-noninteractive
创建一个MySQL帐户,使用与操作系统用户名相同的用户名,并将其定义为使用PAM插件和
mysql-unix
PAM服务:CREATE USER 'antonio'@'localhost' IDENTIFIED WITH 'mysql-unix';授予mydb上的所有特权。*“安东尼奥”@“localhost”;
在这里,身份验证字符串只包含PAM服务名,
mysql-unix
,它对Unix密码进行身份验证。使用mysql命令行客户端连接到MySQL服务器作为
安东尼奥
.例如:$> mysql——user=antonio——password——enable-cleartext-plugin输入密码antonio_password
服务器应该允许连接,下面的查询返回如下所示的输出:
mysql> SELECT USER(), CURRENT_USER(), @@proxy_user;+-------------------+-------------------+--------------+ | 用户()| CURRENT_USER () | @@proxy_user | +-------------------+-------------------+--------------+ | antonio@localhost | antonio@localhost | NULL | +-------------------+-------------------+--------------+
这表明
安东尼奥
操作系统用户通过认证后,才具有权限安东尼奥
MySQL用户,并且没有发生代理。
客户端mysql_clear_password
认证插件保持密码不变,因此客户端程序将其以明文形式发送到MySQL服务器。这使得密码可以像传递给PAM一样传递。使用服务器端PAM库需要明文密码,但在某些配置中可能存在安全问题。以下措施将风险降至最低:
疏忽大意地使用
mysql_clear_password
插件的可能性较小,MySQL客户端必须显式地启用它(例如,使用——enable-cleartext-plugin
选项)。看到第6.4.1.4节,“客户端明文可插入认证”.以避免密码泄露
mysql_clear_password
MySQL客户端应该使用加密连接连接到MySQL服务器。看到第6.3.1节“配置MySQL使用加密连接”.
这个身份验证场景使用PAM检查根据操作系统用户名和LDAP密码定义的外部用户,而不使用代理。每个允许连接到MySQL Server的外部用户都应该有一个匹配的MySQL帐户,该帐户被定义为通过LDAP使用PAM身份验证。
要对MySQL使用PAM LDAP可插入身份验证,必须满足以下先决条件:
LDAP服务器必须可供PAM LDAP服务进行通信。
每个要由MySQL进行身份验证的LDAP用户都必须存在于LDAP服务器管理的目录中。
使用LDAP进行MySQL用户身份验证的另一种方法是使用特定于LDAP的身份验证插件。看到第6.4.1.7节“LDAP可插入认证”.
配置MySQL的PAM LDAP认证如下:
验证Unix身份验证是否允许使用用户名登录到操作系统
安东尼奥
和密码antonio_password
.设置PAM以使用LDAP验证MySQL连接
mysql-ldap
PAM服务文件/etc/pam.d/mysql-ldap
.文件内容与系统相关,因此请检查中现有的与登录相关的文件/etc/pam.d
看看他们长什么样。在Linux上,mysql-ldap
文件可能看起来像这样:#%PAM-1.0认证需要pam_ldap。因此帐户需要pam_ldap.so
如果PAM对象文件的后缀与
所以
在您的系统上,替换正确的后缀。在某些系统上,PAM文件格式可能不同。
创建一个MySQL帐户,使用与操作系统用户名相同的用户名,并将其定义为使用PAM插件和
mysql-ldap
PAM服务:CREATE USER 'antonio'@'localhost' IDENTIFIED WITH ' authentication_pam ' AS 'mysql-ldap'授予mydb上的所有特权。*“安东尼奥”@“localhost”;
在这里,身份验证字符串只包含PAM服务名,
mysql-ldap
,它使用LDAP进行身份验证。连接到服务器的方法与PAM Unix密码认证,无代理用户.
这里描述的身份验证方案使用代理和PAM组映射,将使用PAM进行身份验证的连接MySQL用户映射到定义不同权限集的其他MySQL帐户。用户不直接通过定义权限的帐户进行连接。相反,它们通过使用PAM进行身份验证的默认代理帐户进行连接,这样所有外部用户都映射到拥有特权的MySQL帐户。使用代理帐户连接的任何用户都映射到其中一个MySQL帐户,其权限决定了允许外部用户进行的数据库操作。
这里显示的过程使用Unix密码验证。要使用LDAP,请参见的早期步骤PAM LDAP认证不使用代理用户.
检查传统Unix密码使用/etc/shadow
文件。有关与此文件相关的可能问题的信息,请参见PAM对Unix密码库的身份验证访问.
验证Unix身份验证是否允许使用用户名登录到操作系统
安东尼奥
和密码antonio_password
.验证
安东尼奥
是根
或用户
PAM。设置PAM来验证
mysql-unix
PAM服务通过操作系统用户创建一个名为/etc/pam.d/mysql-unix
.文件内容与系统相关,因此请检查中现有的与登录相关的文件/etc/pam.d
看看他们长什么样。在Linux上,mysql-unix
文件可能看起来像这样:#%PAM-1.0 auth include password-auth account include password-auth
对于macOS,使用
登录
而不是password-auth
.在某些系统上,PAM文件格式可能不同。例如,在Ubuntu和其他基于debian的系统上,使用以下文件内容:
@include common-auth @include common-account @include common-session-noninteractive
创建默认代理用户(
“@”
)将外部PAM用户映射到代理帐户:CREATE USER " @ " WITH authentication_pam AS 'mysql-unix, root=developer, users=data_entry';
在这里,身份验证字符串包含PAM服务名,
mysql-unix
,它对Unix密码进行身份验证。对象中的外部用户也映射为身份验证字符串根
而且用户
PAM组到开发人员
而且data_entry
MySQL用户名。在设置代理用户时,需要使用PAM服务名称后面的PAM组映射列表。否则,插件无法告诉如何执行从外部用户名到适当的代理MySQL用户名的映射。
请注意如果您的MySQL安装有匿名用户,他们可能会与默认的代理用户冲突。有关此问题的更多信息以及处理方法,请参见默认代理用户与匿名用户冲突.
创建代理帐户,并授予每个帐户应该拥有的权限:
CREATE USER 'developer'@'localhost' IDENTIFIED WITH mysql_no_login;CREATE USER 'data_entry'@'localhost' IDENTIFIED WITH mysql_no_login;授予mydevdb上的所有特权。*“开发人员”@“localhost”;授予mydb上的所有特权。*“data_entry”@“localhost”;
代理帐户使用
mysql_no_login
认证插件,防止客户端使用该帐户直接登录MySQL服务器。相反,使用PAM进行身份验证的用户应该使用开发人员
或data_entry
帐户的代理基于他们的PAM组。(这里假设已经安装了插件。说明,请参阅第6.4.1.9节“不可登录可插入认证”)。有关保护代理帐户不被直接使用的其他方法,请参见防止直接登录代理帐户.授予代理帐户
代理
每个代理帐户的权限:将“developer”@“localhost”上的代理授权给“@”将“data_entry”@“localhost”上的代理授权给“@”
使用mysql命令行客户端连接到MySQL服务器作为
安东尼奥
.$> mysql——user=antonio——password——enable-cleartext-plugin输入密码antonio_password
服务器使用默认值验证连接
“@”
代理帐户。的结果特权安东尼奥
取决于哪些PAM组安东尼奥
是的成员。如果安东尼奥
是根
PAM组,PAM插件映射根
到开发人员
MySQL用户名,并将该用户名返回给服务器。服务器进行验证“@”
有代理
特权的开发人员
并允许连接。以下查询返回如下所示的输出:mysql> SELECT USER(), CURRENT_USER(), @@proxy_user;+-------------------+---------------------+--------------+ | 用户()| CURRENT_USER () | @@proxy_user | +-------------------+---------------------+--------------+ | antonio@localhost | developer@localhost | ''@'' | +-------------------+---------------------+--------------+
这表明
安东尼奥
操作系统用户通过认证后,才具有权限开发人员
MySQL用户,该代理通过默认代理帐户进行。如果
安东尼奥
不是会员吗根
PAM组但是是用户
PAM组中,发生类似的过程,但插件映射用户
的PAM组成员资格data_entry
MySQL用户名,并返回给服务器:mysql> SELECT USER(), CURRENT_USER(), @@proxy_user;+-------------------+----------------------+--------------+ | 用户()| CURRENT_USER () | @@proxy_user | +-------------------+----------------------+--------------+ | antonio@localhost | data_entry@localhost | ''@'' | +-------------------+----------------------+--------------+
这表明
安东尼奥
操作系统用户通过认证,具有权限data_entry
MySQL用户,该代理通过默认代理帐户进行。
客户端mysql_clear_password
认证插件保持密码不变,因此客户端程序将其以明文形式发送到MySQL服务器。这使得密码可以像传递给PAM一样传递。使用服务器端PAM库需要明文密码,但在某些配置中可能存在安全问题。以下措施将风险降至最低:
疏忽大意地使用
mysql_clear_password
插件的可能性较小,MySQL客户端必须显式地启用它(例如,使用——enable-cleartext-plugin
选项)。看到第6.4.1.4节,“客户端明文可插入认证”.以避免密码泄露
mysql_clear_password
MySQL客户端应该使用加密连接连接到MySQL服务器。看到第6.3.1节“配置MySQL使用加密连接”.
在某些系统上,Unix身份验证使用密码存储,例如/etc/shadow
,这是一种通常具有受限访问权限的文件。这可能导致MySQL基于pam的身份验证失败。不幸的是,PAM实现不允许进行区分”无法检查密码”(例如,由于不识字/etc/shadow
)”密码不匹配。”如果你使用Unix密码库进行PAM认证,你可以使用以下方法之一从MySQL访问它:
假设MySQL服务器是从
mysql
操作系统帐户,将该帐户放在影子
团体/etc/shadow
访问:创建一个
影子
集团所属
.添加
mysql
操作系统用户到影子
集团所属
.分配
所属
到影子
组并开启组读权限:CHGRP shadow /etc/shadow chmod g+r /etc/shadow
重新启动MySQL服务器。
如果您正在使用
pam_unix
模块和unix_chkpwd实用工具,启用密码存储访问如下:Chmod u-s /usr/sbin/unix_chkpwd setcap cap_dac_read_search+ep /usr/sbin/unix_chkpwd
调整路径为unix_chkpwd作为你的平台所需要的。
PAM身份验证插件在初始化时检查是否AUTHENTICATION_PAM_LOG
设置环境值(值不重要)。如果是,该插件支持将诊断消息记录到标准输出。这些消息可能有助于调试插件执行身份验证时发生的pam相关问题。
一些消息包括对PAM插件源文件和行号的引用,这使得插件操作可以更紧密地与代码中插件操作发生的位置联系在一起。
调试连接失败和确定连接尝试期间发生的情况的另一种技术是配置PAM身份验证以允许所有连接,然后检查系统日志文件。这种方法只适用于临时而不是在生产服务器上。
配置一个名为/etc/pam.d/mysql-any-password
以下内容(格式在某些系统上可能有所不同):
#%PAM-1.0认证需要pam_permit。帐户要求pam_permit
创建一个使用PAM插件并命名为mysql-any-password
PAM服务:
CREATE USER 'testuser'@'localhost' IDENTIFIED WITH 'mysql-any-password';
的mysql-any-password
服务文件导致任何身份验证尝试返回true,即使是错误的密码。如果身份验证尝试失败,则说明配置问题出在MySQL端。否则,问题就出在操作系统/PAM端。要查看可能发生的情况,请检查系统日志文件,例如/var/log/secure
,/var/log/audit.log
,/var/log/syslog
,或/var/log/messages
.
在确定问题是什么之后,删除mysql-any-password
PAM服务文件以禁用任何密码访问。