0

只是修改了 NodeJS/Typescript 应用程序中使用的依赖项,并且遇到了 Helmet 从版本“3.23.2”更改为“4.5.0”的障碍。

我已经从 package.json 文件中删除了依赖项 "@types/helmet": "0.0.47"。

编译会导致以下语义错误:

src/loaders/security.ts(2,18): error TS2305: Module '"helmet"' has no exported member 'IHelmetContentSecurityPolicyDirectives'.
src/options.ts(1,10): error TS2305: Module '"helmet"' has no exported member 'IHelmetContentSecurityPolicyDirectives'.

options.ts 包括:

import { IHelmetContentSecurityPolicyDirectives } from 'helmet';

export interface Options {
  redirectUrl: string;
  mountPath: string;
  serviceName?: string;
  views?: string | string[];
  csp?: IHelmetContentSecurityPolicyDirectives;
  i18n?: I18nOptions;
}

security.ts 定义为:

import { Application } from 'express';
import helmet, { IHelmetContentSecurityPolicyDirectives } from 'helmet';
import logger from '../lib/logger';

const configureSecurity = (app: Application, csp: IHelmetContentSecurityPolicyDirectives | undefined): void => {
  logger.info('Configuring Security using Helmet');
  const defaultSrc = (csp && csp.defaultSrc) || [];
  const styleSrc = (csp && csp.styleSrc) || [];
  const scriptSrc = (csp && csp.scriptSrc) || [];
  app.use(helmet({
    contentSecurityPolicy: {
      directives: {
        defaultSrc: [...defaultSrc, "'self'"],
        styleSrc: [...styleSrc, "'self'"],
        scriptSrc: [
          ...scriptSrc,
          "'self'",
          "'sha256-+XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX'",
          "'sha256-+XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX'",
        ],
      },
    },
  }));
};

export default configureSecurity;

我不知道用什么来代替IHelmetContentSecurityPolicyDirectivescsp 类型。

4

1 回答 1

0

头盔的维护者在这里。

Helmet v3 没有官方的 TypeScript 定义,而 Helmet v4 有。简而言之,您会看到这个问题,因为 Helmet v3 的社区制作类型没有干净地映射到 Helmet v4 中的官方类型。

您正在寻找IHelmetContentSecurityPolicyDirectives. 这是Helmet 的 Content Security Policy 模块的官方类型定义的片段

export interface ContentSecurityPolicyOptions {
  directives?: Record<
    string,
    | Iterable<ContentSecurityPolicyDirectiveValue>
    | typeof dangerouslyDisableDefaultSrc
  >;
  reportOnly?: boolean;
}

directives关键是旧人的ContentSecurityPolicyOptions“转世” IHelmetContentSecurityPolicyDirectives

我看到两个选项:

  1. 自己定义类型,然后使用它。例如:

    type CspDirectiveValue =
      | string
      | ((req: IncomingMessage, res: ServerResponse) => string);
    
    type CspDirectives = Record<string, Iterable<CspDirectiveValue>>;
    

    然后,您可以使用CspDirectives代替旧IHelmetContentSecurityPolicyDirectives类型。

  2. 稍微修改一下你的代码。

    您可以更新Options界面以获取Helmet 的所有选项:

    import helmet from 'helmet';
    
    export interface Options {
      // ...
      helmetOptions: Parameters<typeof helmet>[0];
      // ...
    }
    

    然后你可以使用它configureSecurity

    const configureSecurity = (app: Application, helmetOptions: Parameters<typeof helmet>[0]): void => {
      // ...
      app.use(helmetOptions);
    };
    

    您的实际代码可能会有所不同。

于 2021-04-29T03:19:25.337 回答