跳转至

示例:仅允许来自企业网络内部的注册(使用 Hook)

Authany Webhook 是一项功能,会在特定事件发生时,以 HTTP 请求的形式向您指定的外部 URL 发送通知。例如,Webhook 可以在新用户创建之前发送 user.pre_create 事件。

Webhook 还会监听来自外部服务的响应。对于阻塞事件,该响应决定了触发事件的流程应该继续完成还是被终止。在本文中,我们将使用一个阻塞事件和一个自定义 Webhook 端点,把用户注册限制为仅允许来自企业网络内部的设备。

如何使用 Webhook 阻止或允许用户注册

为 user.pre-created 事件配置 Webhook 后,如果您的 Webhook 端点在响应中返回 is_allowed: false,Authany 就不会创建新用户;反之,如果端点在响应中返回 is_allowed: true,新用户将被成功创建。

我们将利用这一机制,通过检查用户的 IP 地址(该地址包含在 Authany 发出的 Webhook HTTP 请求的负载中)来阻止企业网络之外的用户注册。当 IP 地址与指定的允许 IP 地址匹配时,我们将 is_allowed 的值设为 true;否则返回 false。

下面的教程详细介绍了如何只允许来自企业网络内部的用户注册。

步骤 1:在 Authany 管理台配置 Webhook

在这一步中,我们将在 Authany 管理台为 User pre-create 事件创建一个 Webhook。为此,登录 Authany 管理台,进入高级 > Hook。然后在阻塞事件部分点击新增,将类型选择为 Webhook,事件选择为 User pre-create。

在端点文本框中,输入用于接收和处理 Webhook 请求的页面完整 URL。

完成后,点击顶部的保存按钮。

步骤 2:创建端点

您需要使用自己熟悉的编程语言或框架创建一个端点,并将其部署到线上。本教程将创建一个基础的 Express.js 端点。

创建一个新的 Express.js 项目,并将以下代码添加到 app.js 中:

const express = require("express");
const app = express();
const bodyParser = require('body-parser');
const port = process.env.PORT || 3002;
app.use(bodyParser.json());

app.post('/', (request, response) => {

    response.status(200).send(
        {
            "is_allowed": false,
            "reason": "some reason",
            "title": "some title"
          }
    );
});

app.listen(port, () => {
    console.log("server started!");
});

让我们来看看上面这段代码的作用:

  • Express 创建了一个接受 POST 请求的端点。(请注意,Authany Webhook 只会发送 POST HTTP 请求,且您的端点必须支持 HTTPS。)
  • 部署上述代码,并将 Authany Webhook 端点指向它,会阻止所有用户注册。
  • 这是因为该代码会向 Webhook 返回 is_allowed: false,从而终止注册流程。
  • 您还可以在端点响应中使用 reason 字段,说明更详细的终止原因。

步骤 3:读取 Webhook 请求中的数据

Authany Webhook 会向端点 URL 发送数据,方便开发者构建自定义功能等。在这一步中,我们将从 User pre-created 事件调用中读取数据,获取尝试注册用户的 IP 地址。

要读取请求正文并将其输出到控制台,请在 response.status(200)... 上方新起一行,添加以下代码:

const requestPayload = request.body;
console.log(requestPayload)

再次尝试注册新用户时,端点控制台应会打印出类似下面的负载数据:

{
    id: '0000000000022b55',
    seq: 142165,
    type: 'user.pre_create',
    payload: {
      user: {
        id: '413fe869-dba2-43a8-b671-95fd471b7950',
        created_at: '2023-08-14T03:44:36.383367Z',
        updated_at: '2023-08-14T03:44:36.473456Z',
        is_anonymous: false,
        is_verified: true,
        is_disabled: false,
        is_deactivated: false,
        is_anonymized: false,
        can_reauthenticate: true,
        standard_attributes: [Object],
        x_web3: [Object]
      },
      identities: [ [Object] ]
    },
    context: {
      timestamp: 1691984676,
      user_id: '413fe869-dba2-43a8-b671-95fd471b7950',
      triggered_by: 'user',
      audit_context: null,
      preferred_languages: [ 'en-US', 'en' ],
      language: 'en',
      ip_address: '123.456.78.009',
      user_agent: 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:109.0) Gecko/20100101 Firefox/116.0',
      app_id: 'my_test_app'
    }
  }

在本例中,我们关心的数据是 context 对象中的 ip_address(context.ip_address)。我们将使用这个 IP 地址来判断用户是否位于企业网络内部。

现在,更新 app.js,使其在用户 IP 地址属于企业网络 IP 地址范围时返回 is_allowed: true。

修改后的 app.js 代码应如下所示:

app.post('/', (request, response) => {

    const requestPayload = request.body;
    console.log(requestPayload)

    const allowedIp = '123.456.78.009'; //replace the value with the corporate network IP address 
    if (requestPayload.context.ip_address == $orgIp) {

        //this user is from the organisation network, continue with sign up.
        response.status(200).type('json').send(
            {
                "is_allowed": true
              }
        );

    } else {
        //user has an IP address outside of the organisation network so disallow sign up.
        response.status(200).type('json').send(
            {
                "is_allowed": false,
                "reason": "You are not allow to sign up to this organisation",
                "title": "Sign-up not allowed!"
              }
        )
    }

});

请将 allowedIp 的值替换为您希望允许的 IP 地址。

此时,如果部署该端点并从允许的 IP 尝试注册,流程应能顺利完成,说明您已经成功实现了仅允许企业网络内部注册的功能。

使用 JavaScript/TypeScript Hook 只允许企业网络内部注册

除了常规 Webhook,Authany 还提供了另一种方式,即 JavaScript/TypeScript Hook。使用这类 Hook,无需托管外部端点即可实现前面的方案。接下来,我们将介绍如何使用 TypeScript Hook 实现只允许企业网络内部用户注册。

步骤 1:在 Authany 管理台配置 TypeScript Hook

在 Authany 管理台进入高级 > Hook。然后在阻塞事件部分点击新增,或者直接修改前面创建的 Webhook。

将类型选择为 TypeScript,事件选择为 User pre-create。

TypeScript Hook 的第三个字段与常规 Webhook 不同。该字段可以让您输入 JavaScript 代码,在事件触发时由 Hook 执行。

您可以点击脚本字段旁边的编辑脚本按钮,打开 Hook 脚本编辑器。

步骤 2:编写 Hook 的 JavaScript 代码

将脚本编辑器中的代码修改为以下内容:

export default async function (e: EventUserPreCreate): Promise<HookResponse> {
  // Write your hook with the help of the type definition.
  const allowedIp = "123.456.78.009";
  if (e.context.ip_address == allowedIp) {
    return {
      is_allowed: true,
    };
  } else {
    return {
      is_allowed: false,
      reason: "You are not allow to sign up to this organisation",
      title: "Sign-up not allowed!",
    };
  }
}

请务必将 allowedIp 的值改为您希望允许的 IP 地址。

完成后,点击完成编辑返回 Hook 配置页面,再点击配置页面顶部的保存按钮保存新的 Hook。

步骤 3:测试 Hook

要测试 TypeScript Hook 是否正常工作,请尝试从之前指定的 IP 地址注册新用户,再尝试从该 IP 地址之外注册,确认结果是否符合预期。