Web 安全

未匹配的标注

你可以使用 @adonisjs/shield 包保护网页应用,使其免受像 CSRFXSS内容嗅探 等一般网页攻击。

使用 AdonisJS 创建服务端渲染应用时,建议使用这个包。

如果你使用 AdonisJS 创建 API 服务器,你就必须依赖前端框架的安全层。

// title: 安装
npm i @adonisjs/shield
// title: 配置
node ace configure @adonisjs/shield
// title: 注册中间件
// 添加到 start/kernel.ts

Server.middleware.register([
  () => import('@ioc:Adonis/Core/BodyParser'),
  // highlight-start
  () => import('@ioc:Adonis/Addons/Shield')
  // highlight-end
])

CSRF 保护

CSRF (Cross-Site Request Forgery) 跨站请求伪造是指欺骗网站用户在未经其明确同意之下,执行表单提交的攻击。

要使其免受 CSRF 攻击,你的应用应该能够区分表单的提交是来自于你的应用还是其他恶意网站。

AdonisJS 为每个请求生成一个唯一的 token (被称做 CSRF Token)值,并将其与用户 session 关联,以供后续验证使用。因此,token 在后端生成,恶意网站没有办法获取。

Token 必须与其他表单字段一起提交,才能通过 CSRF 检测。你可以在模板中使用 csrfField 来获取它。

<form action="{{ route('PostsController.store') }}" method="post">
  // highlight-start
  {{ csrfField() }}
  // highlight-end

  <div>
    <label for="title">Post title</label>
    <input type="text" name="title">
  </div>
  <hr>

  <button type="submit">Create Post</button>
</form>

这就是你需要做的。

配置

shield 中间件依赖于存储在 config/shield.ts 文件中的配置,随意根据你的要求调整配置选项。

export const csrf: ShieldConfig['csrf'] = {
  enabled: true,
  exceptRoutes: [],
  enableXsrfCookie: true,
  methods: ['POST', 'PUT', 'PATCH', 'DELETE'],
}

enabled

全部启用/禁用 CSRF 保护。在直接点击表单按钮时,你可能会发现自己在测试期间禁用了它。


exceptRoutes

忽略针对 CSRF 令牌验证的某些路由。在创建具有 API 端点和服务器呈现表单的混合应用程序时,你可能会发现它很有用,方法是使 API 端点免于 CSRF 令牌验证。

{
  exceptRoutes: [
    '/api/users',
    '/api/users/:id',
    '/api/posts'
  ]
}

对于更高级的用例,你可以注册一个函数并动态过滤路由以防止被验证。

{
  exceptRoutes: (ctx) => {
    // 忽略所有以 /api/ 开头的路由
    return ctx.request.url().includes('/api/')
  }
}

methods

用于验证 CSRF 令牌可用性的 HTTP 方法。你必须添加所有用于处理表单提交的 HTTP 动作。

{
  methods: ['POST', 'PUT', 'PATCH', 'DELETE']
}

enableXsrfCookie

将该值设置为 true 指示屏蔽中间件从 X-XSRF-TOKEN 标头读取 CSRF 令牌。阅读 Ajax 表单提交 部分以了解更多信息。


SPA 的 CSRF 令牌

单页应用程序在前端呈现表单,因此它们无法访问 csrfField 全局视图。但是,你可以从 XSRF-TOKENcookie 中读取令牌值,并通过 X-XSRF-TOKEN 标头将其发送到服务器。

cookie 技术已经被 Angular 等框架和 axios 等请求库广泛支持。

但是,请确保通过在 config/shield.ts 文件中设置 enableXsrfCookie = true 来启用 cookie 功能。

用于 RESTful API 的 CSRF 令牌

如果你正在创建 RESTful API 服务器,则不需要 CSRF 保护,除非依赖 cookie 进行用户身份验证。如果你依赖 cookie 进行身份验证,则只需按照 CSRF token for SPA 部分的说明进行操作。

CSP

CSP (Content security policy) 帮助你定义加载和执行scriptsstylesfonts等的可信来源并降低 XSS 攻击的风险。

你可以通过调整 config/shield.ts 文件中的配置选项来配置 CSP 标头。

// 文件名: config/shield.ts
export const csp: ShieldConfig['csp'] = {
  enabled: false,
  directives: {},
  reportOnly: false,
}

enabled

一起启用/禁用 CSP 保护。


directives

配置 CSP 标头指令。我们建议在 https://content-security-policy.com 上阅读它们。dash-case 指令名称在 shield 配置文件中定义为 camelCase

directives: {
  defaultSrc: ["'self'"],
  scriptSrc: ["'self'", 'https://cdnjs.cloudflare.com', '@nonce'],
  fontSrc: ["'self'", 'https://fonts.googleapis.com'],
}

reportOnly

如果你希望 CSP 违规导致警告而不是错误,请将值设置为 true。 了解更多


CSP 随机数(nonce)

要定义 nonce-based 内联脚本和样式标签,必须使用 @nonce 关键字。

directives: {
  scriptSrc: ["'self'", '@nonce'],
}

接下来,使用 cspNonce 视图助手来定义内联脚本和样式标签的 nonce 属性。

<script nonce="{{ cspNonce }}">
</script>

你还可以使用 response.nonce 属性访问 nonce 属性。

Route.get('/', ({ response }) => {
  return {
    nonce: response.nonce
  }
})

DNS 预取(prefetching)

使用 config/shield.ts 文件中的 dnsPrefetch 设置,你可以控制 [X-DNS-Prefetch-Control](developer.mozilla. org/en-US/docs/Web/HTTP/Headers/X-DNS-Prefetch-Control) 标头。

export const dnsPrefetch: ShieldConfig['dnsPrefetch'] = {
  enabled: true,
  allow: true,
}

enabled

一起启用/禁用头部。


allow

将该值设置为 true 将定义具有值 'on'X-DNS-Prefetch-Control 标头,否则定义 'off' 值。

帧保护

xFrame 配置属性管理 X-Frame-Options 标头。

export const xFrame: ShieldConfig['xFrame'] = {
  enabled: true,
  action: 'DENY',
}

enabled

一起启用/禁用标题。


action

定义标题值。它必须是 DENYSAMEORIGINALLOW-FROM 之一。ALLOW-FROM 动作也需要域名允许。

{
  enabled: true,
  action: 'ALLOW-FROM',
  domain: 'foo.com'
}

HSTS

使用 Strict-Transport-Security 标头控制是否应通过 HTTP 访问网站.

HSTS 的配置存储在 config/shield.ts 文件中。

export const hsts: ShieldConfig['hsts'] = {
  enabled: true,
  maxAge: '180 days',
  includeSubDomains: true,
  preload: false,
}

enabled

同时启用/禁用Strict-Transport-Security


maxAge

定义浏览器应该记住标头值的时间。


includeSubDomains

当设置为true时,该规则也将应用于站点的子域。


preload

是否从 HSTS 预加载服务中预加载标头值。 了解更多

No sniffing

使用contentTypeSniffing设置,您可以控制 X-Content-Type-Options 头信息。

仅当enabled属性设置为 true 时才设置标头。

export const contentTypeSniffing: ShieldConfig['contentTypeSniffing'] = {
  enabled: true,
}

本文章首发在 LearnKu.com 网站上。

本译文仅用于学习和交流目的,转载请务必注明文章译者、出处、和本文链接
我们的翻译工作遵照 CC 协议,如果我们的工作有侵犯到您的权益,请及时联系我们。

原文地址:https://learnku.com/docs/adonisjs/5.x/se...

译文地址:https://learnku.com/docs/adonisjs/5.x/se...

上一篇 下一篇
贡献者:3
讨论数量: 0
发起讨论 只看当前版本


暂无话题~