macfly/yii2-webserver-auth

该包已被废弃且不再维护。未建议替代包。

为Yii框架提供的Nginx和Httpd认证模块

安装: 104

依赖者: 0

建议者: 0

安全性: 0

星标: 1

关注者: 1

分支: 1

开放问题: 0

类型:yii2-extension

0.2.1 2017-12-11 03:55 UTC

This package is auto-updated.

Last update: 2023-04-13 03:40:24 UTC


README

此模块允许您限制对Nginx或Apache HTTPD服务器后面任何网站的访问。使用此模块,您的Yii网站将成为您的认证和授权提供者,就像LDAP或htaccess文件一样。

一些有用的用法

  • 在多个Web服务器上共享登录和密码(无需在各个地方更新htaccess以更新密码),可以直接在您的Yii网站上完成。
  • 如果HTTPD或Nginx后面的网站不在HTTPS上,认证基于访问令牌(默认情况下),如果您的令牌寿命不长且随机,它可以接受用于安全目的(始终建议使用ssl)。
  • 在Nginx中,您有单点登录功能,如果您已经登录到您的Yii网站,您将看不到任何登录页面(仅在所有网站都共享父域名以访问cookie时才有效)。
  • 权限管理同一个账户可以访问不同的网站,可以访问site1但不能访问site2。

测试

example目录中有一个Apache HTTPD和Nginx的完整docker-compose示例,只需执行

git clone https://github.com/marty-macfly/yii2-webserver-auth.git
cd yii2-webserver-auth/example/yii
composer update
cd ..
docker-compose build
docker-compose up

yii站点只是安装了扩展的yii基本模板

您可以访问以下组件

有两个用户

  • admin/admin => 访问令牌:100-token
  • demo/demo => 访问令牌:101-token

登录和密码仅用于Nginx上的单点登录,当您重定向到http://127.0.0.1:8080/site/login时。如果您的浏览器直接提示登录和密码,您应使用登录:x-sso-token(在模块配置中定义的token_name的名称)和访问令牌作为密码(对于admin用户100-token)。

Yii设置

安装

通过composer安装此扩展是首选方式。

运行以下命令之一

php composer.phar require --prefer-dist "macfly/yii2-webserver-auth" "*"

或添加

"macfly/yii2-webserver-auth": "*"

到您的composer.json文件的require部分。

配置

按照以下方式配置config/web.php

  'modules' => [
     ................
    'htaccess'  => [
      'class' => 'macfly\yii\webserver\Module',
      // 'token_name' => 'mycookie', // You can change the name of the login/cookie/header in which the authentication token will be set/get
    ],
    ................
  ],

模块 bootstrap 将在 user 组件处理器的 macfly\yii\webserver\events\NginxAuthEvent->setTokenCookie 上附加于 afterLogin,并在 macfly\yii\webserver\events\NginxAuthEvent->unsetTokenCookie 上附加于 afterLogout

Nginx 配置

安装

您需要安装 Nginx Auth Request 模块 ngx_http_auth_request_module

  • 在 Debian 上,该模块由 nginx-extras 提供,因此要安装,您只需执行以下操作
apt-get install nginx-extras

配置

您需要更新您想要限制的站点的 Nginx 配置,添加以下元素

server {
    listen       80;
    server_name  www.website.com;

    location / {
        # We want to protect the root of our website
        auth_request /auth;

        root   /usr/share/nginx/html;
        index  index.html index.htm;

        error_page 401 = @error401;
        error_page 403 = @error403;
    }

    location @error401 {
        # If you want the user to come back here after successful login add
        # the following query string "?return_url=http://www.website.com"
        return 302 http://yii.website.com/site/login?return_url=${scheme}://${http_host}${request_uri};
        # If you don't want the user to be redirect back just remove
        # the query string
        # return 302 http://yii.website.com/site/login;
    }

    location @error403 {
        return 403;
    }

    location = /auth {
        internal;

        rewrite ^(.*)$                  /htaccess/auth? break;
        proxy_pass                      http://yii.website.com;
        proxy_pass_request_headers      on;

        # Don't forward useless data
        proxy_pass_request_body         off;
        proxy_set_header Content-Length "";
    }
}

您可以在 example/nginx/ 目录中找到更详细的 配置

使用方法

从浏览器访问

当您访问 http://www.website.com 时,如果您没有定义由 token_name (默认:x-sso-token)或 identityCookie 定义的 cookie,您的浏览器将被重定向到 http://yii.website.com/site/login。登录后,您可以再次访问 http://www.website.com 并获得对站点的访问权限(如果您的用户具有相应的权限)。

从命令行访问

您也可以使用命令行工具(如 wgetcurl)进行身份验证,在这种情况下,您可以使用两种方法

$ curl -s -i -X GET --header 'Authorization: Bearer 100-token' 'http://127.0.0.1:8888/user-sso/'
HTTP/1.1 200 OK
Server: nginx/1.10.3
Date: Tue, 28 Nov 2017 05:33:01 GMT
Content-Type: text/html
Content-Length: 359
Last-Modified: Mon, 27 Nov 2017 10:19:20 GMT
Connection: keep-alive
ETag: "5a1be6a8-167"
Accept-Ranges: bytes

<!DOCTYPE html>
<html>%   
<head>
<title>Welcome to restricted section!</title>
<style>
    body {
        width: 35em;
        margin: 0 auto;
        font-family: Tahoma, Verdana, Arial, sans-serif;
    }
</style>
</head>
<body>
<h1>Welcome to restricted section!</h1>
<p>You can see this page because you're a logged in user, sso was used.</p>
</body>
</html>

使用无效的令牌

$ curl -s -i -X GET --header 'Authorization: Bearer bad-token' 'http://127.0.0.1:8888/user-sso/'
HTTP/1.1 401 Unauthorized
Server: nginx/1.10.3
Date: Tue, 28 Nov 2017 05:35:18 GMT
Content-Type: application/octet-stream
Content-Length: 57
Connection: keep-alive

Unauthorized: You didn't provide the authentication token

如果您没有权限访问位置(仅在 sso 模式下,如果您使用 no-sso 测试,则返回代码将为 401)

$ curl -s -i -X GET --header 'Authorization: Bearer 100-token' 'http://127.0.0.1:8888/permission-sso/'
HTTP/1.1 403 Forbidden
Server: nginx/1.10.3
Date: Tue, 28 Nov 2017 05:36:01 GMT
Content-Type: application/octet-stream
Content-Length: 61
Connection: keep-alive

Forbidden: You don't have permissions to access that resource
  • 提供登录/密码的访问令牌,访问令牌作为用户名发送
$ curl -s -i -X GET 'http://100-token:@127.0.0.1:8888/user/'
HTTP/1.1 200 OK
Server: nginx/1.10.3
Date: Tue, 28 Nov 2017 05:39:52 GMT
Content-Type: text/html
Content-Length: 359
Last-Modified: Mon, 27 Nov 2017 10:19:20 GMT
Connection: keep-alive
ETag: "5a1be6a8-167"
Accept-Ranges: bytes

<!DOCTYPE html>
<html>
<head>
<title>Welcome to restricted section!</title>
<style>
    body {
        width: 35em;
        margin: 0 auto;
        font-family: Tahoma, Verdana, Arial, sans-serif;
    }
</style>
</head>
<body>
<h1>Welcome to restricted section!</h1>
<p>You can see this page because you're a logged in user, sso was used.</p>
</body>
</html>

Apache Httpd 配置

安装

您需要安装并启用模块 mod_authnz_external

  • 在 Debian 上,该模块由 libapache2-mod-authnz-external 提供,因此要安装,您只需执行以下操作
apt-get install libapache2-mod-authnz-external

由于我们使用 shell 脚本来进行请求,因此您还需要安装 curl

apt-get install curl

您需要将脚本 apache-auth.sh 放置在服务器上,该脚本将启动适当的 curl 命令

配置

您需要更新您想要限制的站点的 Httpd 服务器配置,添加以下元素

<VirtualHost *:80>
	ServerName www.website.com
	DocumentRoot /var/www/html

	DefineExternalAuth auth pipe '/apache-auth.sh http://yii.website.com/htaccess/auth'

	<Directory "/var/www/html/user">
		Options Indexes FollowSymLinks

		AuthType Basic
		AuthName "Authentication Required"
		Require valid-user
		AuthBasicProvider external
		AuthExternal auth
		AllowOverride None
	</Directory>
</VirtualHost>

您可以在 example/httpd/ 目录中找到更详细的 配置

从命令行访问

您也可以使用命令行工具(如 wgetcurl)进行身份验证,在这种情况下,您可以使用以下方法

  • 提供登录/密码的访问令牌,访问令牌作为用户名发送
$ curl -s -i -X GET 'http://100-token:@127.0.0.1:8889/user/'
HTTP/1.1 200 OK
Date: Tue, 28 Nov 2017 05:44:46 GMT
Server: Apache/2.4.25 (Debian)
Last-Modified: Mon, 27 Nov 2017 10:58:40 GMT
ETag: "159-55ef4c8f3b800"
Accept-Ranges: bytes
Content-Length: 345
Vary: Accept-Encoding
Content-Type: text/html

<!DOCTYPE html>
<html>
<head>
<title>Welcome to restricted section!</title>
<style>
    body {
        width: 35em;
        margin: 0 auto;
        font-family: Tahoma, Verdana, Arial, sans-serif;
    }
</style>
</head>
<body>
<h1>Welcome to restricted section!</h1>
<p>You can see this page because you're a logged in user.</p>
</body>
</html>

使用无效的令牌

$ curl -s -i -X GET 'http://bad-token:@127.0.0.1:8889/user/'
HTTP/1.1 401 Unauthorized
Date: Tue, 28 Nov 2017 05:45:27 GMT
Server: Apache/2.4.25 (Debian)
WWW-Authenticate: Basic realm="Authentication Required"
Content-Length: 458
Content-Type: text/html; charset=iso-8859-1

<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>401 Unauthorized</title>
</head><body>
<h1>Unauthorized</h1>
<p>This server could not verify that you
are authorized to access the document
requested.  Either you supplied the wrong
credentials (e.g., bad password), or your
browser doesn't understand how to supply
the credentials required.</p>
<hr>
<address>Apache/2.4.25 (Debian) Server at 127.0.0.1 Port 8889</address>
</body></html>