eggjs获取客户端真实ip的方法

栏目: EggJs 发布时间:2024-11-01

在Egg.js中,你可以通过以下步骤获取用户端的真实IP地址:

确保你的服务器使用了反向代理,例如Nginx。

在Egg.js的Controller层中,可以通过ctx.request.ip来获取客户端的IP地址。但是,这个值可能是代理服务器提供的IP地址,而不是真实的客户端IP地址。 为了获取真实的客户端IP地址,你可以使用ctx.request.headers['x-forwarded-for']。这个值是代理服务器提供的客户端IP地址列表,通常第一个值是真实的客户端IP地址。

以下是一个示例代码:

const Controller = require('egg').Controller;  
  
class UserController extends Controller {  
  async getIp() {  
    const ip = this.ctx.request.headers['x-forwarded-for'] || this.ctx.request.ip;  
    this.ctx.body = ip;  
  }  
}  
  
module.exports = UserController;

在上述代码中,getIp()方法通过检查x-forwarded-for头部的值来获取真实的客户端IP地址。如果该头部不存在或为空,则使用 ctx.request.ip 作为备用值。最后,将获取到的IP地址作为响应返回给客户端。

开启前置代理模式

通过 config.proxy = true,可以打开前置代理模式:

// config/config.default.js
exports.proxy = true;

注意,开启此模式后,应用就默认自己处于反向代理之后,会支持通过解析约定的请求头来获取用户真实的 IP,协议和域名。如果你的服务未部署在反向代理之后,请不要开启此配置,以防被恶意用户伪造请求 IP 等信息。

config.ipHeaders

开启 proxy 配置后,应用会解析 X-Forwarded-For 请求头来获取客户端的真实 IP。如果你的前置代理通过其他的请求头来传递该信息,可以通过 config.ipHeaders 来配置,这个配置项支持配置多个头(逗号分开)。

// config/config.default.js
exports.ipHeaders = 'X-Real-Ip, X-Forwarded-For';

config.maxIpsCount

X-Forwarded-For 等传递 IP 的头,通用的格式是:

X-Forwarded-For: client, proxy1, proxy2

我们可以拿第一个作为请求的真实 IP,但是如果有恶意用户在请求中传递了 X-Forwarded-For 参数来伪造其在反向代理之后,就会导致 X-Forwarded-For 拿到的值不准确了,可以被用来伪造请求 IP 地址,突破应用层的一些 IP 限制。

X-Forwarded-For: fake, client, proxy1, proxy2

为了避免此问题,我们可以通过 config.maxIpsCount 来配置前置的反向代理数量,这样在获取请求真实 IP 地址时,就会忽略掉用户多传递的伪造 IP 地址了。例如我们将应用部署在一个统一的接入层之后(例如阿里云 SLB),我们可以将此参数配置为 1,这样用户就无法通过 X-Forwarded-For 请求头来伪造 IP 地址了。

// config/config.default.js
exports.maxIpsCount = 1;

此配置项与 koa 提供的 options.maxIpsCount 作用一致。

config.protocolHeaders

开启 proxy 配置后,应用会解析 X-Forwarded-Proto 请求头来获取客户端的真实访问协议。如果你的前置代理通过其他的请求头来传递该信息,可以通过 config.protocolHeaders 来配置,这个配置项支持配置多个头(逗号分开)。

// config/config.default.js
exports.protocolHeaders = 'X-Real-Proto, X-Forwarded-Proto';

config.hostHeaders

开启 proxy 配置后,应用仍然还是直接读取 host 来获取请求的域名,绝大部分反向代理并不会修改这个值。但是也许有些反向代理会通过 X-Forwarded-Host 来传递客户端的真实访问域名,可以通过在 config.hostHeaders 中配置,这个配置项支持配置多个头(逗号分开)。

// config/config.default.js
exports.hostHeaders = 'X-Forwarded-Host';

本文地址:https://www.tides.cn/p_eggjs-get-real-ip-of-client