javascript 当`instanceof`出现问题时

u0sqgete  于 2023-05-27  发布在  Java
关注(0)|答案(1)|浏览(139)

我最近在GitHub上提交了一个问题,但该项目似乎不是很活跃,所以我不确定它是否会影响到许多其他开发人员。
以下是问题的链接:https://github.com/Urigo/graphql-modules/issues/2337
为了给予一点上下文,我目前正在使用TypeScript编写的GraphQL API,并使用graphql-modules库在其函数之一中调用instanceof
下面是上述函数的代码(修改后添加了一些日志记录):

function isScalarResolver(obj) {
    console.log('obj:', obj, '\nisScalarResolver(obj):', obj instanceof GraphQLScalarType, '\n');
    return obj instanceof GraphQLScalarType;
}

运行pnpm run test后,终端中显示的输出如下:

obj: { now: [Function: now] }
isScalarResolver(obj): false

obj: GraphQLScalarType {
  name: 'DateTime',
  description: 'DateTime scalar type',
  specifiedByURL: undefined,
  serialize: [Function: serialize],
  parseValue: [Function: parseValue],
  parseLiteral: [Function: parseLiteral],
  extensions: [Object: null prototype] {},
  astNode: undefined,
  extensionASTNodes: []
}
isScalarResolver(obj): false

在我看来,objGraphQLScalarType的一个示例,所以obj instanceof GraphQLScalarType应该返回true(实际上运行pnpm run dev时就是这种情况)。
对于那些想了解这个问题的人,StackBlitz上有一个复制品:https://stackblitz.com/github/devatina11yb/graphql-modules
复制步骤:
1.打开StackBlitz上的代码。
1.在终端中运行命令open /home/projects/qgnikzovb.github/node_modules/.pnpm/graphql-modules@2.1.2_graphql@16.6.0/node_modules/graphql-modules/index.mjs(它将在编辑器中打开文件)。
1.通过添加console.log('obj:', obj, '\nisScalarResolver(obj):', obj instanceof GraphQLScalarType, '\n');来更改第1859行的函数isScalarResolver
1.在终端中运行pnpm run test命令。
1.您将得到上面提到的输出。
您还可以通过在终端中运行pnpm run dev命令来确认代码运行无误。
以下是运行pnpm run dev后的输出:

obj: { now: [Function: now] }
isScalarResolver(obj): false

obj: GraphQLScalarType {
  name: 'DateTime',
  description: 'DateTime scalar type',
  specifiedByURL: undefined,
  serialize: [Function: serialize],
  parseValue: [Function: parseValue],
  parseLiteral: [Function: parseLiteral],
  extensions: [Object: null prototype] {},
  astNode: undefined,
  extensionASTNodes: []
}
isScalarResolver(obj): true

obj: {
  now: [Function: now] { [Symbol(metadata)]: { moduleId: 'scalars' } }
}
isScalarResolver(obj): false

obj: GraphQLScalarType {
  name: 'DateTime',
  description: 'DateTime scalar type',
  specifiedByURL: undefined,
  serialize: [Function: serialize] { [Symbol(metadata)]: { moduleId: 'scalars' } },
  parseValue: [Function: parseValue] { [Symbol(metadata)]: { moduleId: 'scalars' } },
  parseLiteral: [Function: parseLiteral] {
    [Symbol(metadata)]: { moduleId: 'scalars' }
  },
  extensions: [Object: null prototype] {},
  astNode: undefined,
  extensionASTNodes: []
}
isScalarResolver(obj): true

编辑1

通过调试器进一步调查后,发现GraphQLScalarType类似乎是从不同的文件加载的:node_modules/.pnpm/graphql@16.6.0/node_modules/graphql/type/definition.jsnode_modules/.pnpm/graphql@16.6.0/node_modules/graphql/type/definition.mjs导致instanceof返回false
这实际上被称为“双包危害”,同时加载CJS和ESM包。所以graphql-js是这个问题的来源,它已经在GitHub上被报告了多次。

hgqdbh6s

hgqdbh6s1#

这通常发生在您多次安装相同的软件包时(在不同的路径上)。确保您的代码和所有依赖项从同一位置导入完全相同的模块。
一个原因可能是您安装了多个依赖于同一个包的不同版本的依赖项(在本例中为graphql-js)。使用锁定文件确保只使用一个版本。

相关问题