Gatsby项目迁移到TypeScript

示例仓库 https://github.com/XYShaoKang...

迁移步骤:

  • TS 配置
  • 配置 ESLint 支持 TS
  • 使用gatsby-plugin-codegen完善 GraphQL 类型提示

初始化项目

gatsby new gatsby-migrate-to-typescript XYShaoKang/gatsby-project-config

cd gatsby-migrate-to-typescript

yarn develop

TS 配置

  • 安装typescript
  • 添加typescript.json配置文件
  • 修改 js 文件为 tsx
  • 补全 TS 声明定义

安装typescript

yarn add -D typescript

添加配置文件tsconfig.json

// https://www.typescriptlang.org/v2/docs/handbook/tsconfig-json.html

{

"compilerOptions": {

"target": "esnext", // 编译生成的目标 es 版本,可以根据需要设置

"module": "commonjs", // 编译生成的目标模块系统

"lib": ["dom", "es2015", "es2017"], // 配置需要包含的运行环境的类型定义

"jsx": "react", // 配置 .tsx 文件的输出模式

"strict": true, // 开启严格模式

"esModuleInterop": true, // 兼容 CommonJS 和 ES Module

"noUnusedLocals": true, // 报告未使用的局部变量的错误

"noUnusedParameters": true, // 报告有关函数中未使用参数的错误

"experimentalDecorators": true, // 启用装饰器

"emitDecoratorMetadata": true, // 支持装饰器上生成元数据,用来进行反射之类的操作

"noEmit": true, // 不输出 js,源映射或声明之类的文件,单纯用来检查错误

"skipLibCheck": true // 跳过声明文件的类型检查,只会检查已引用的部分

},

"exclude": ["./node_modules", "./public", "./.cache"], // 解析时,应该跳过的路晋

"include": ["src"] // 定义包含的路径,定义在其中的声明文件都会被解析进 vscode 的智能提示

}

index.js改成index.tsx,重新启动服务,查看效果.

补全 TS 声明定义

打开index.tsx,VSCode 会报两个错误,一个是找不到styled-components的声明文件,这个可以通过安装@types/styled-components来解决.

另外一个错误绑定元素“data”隐式具有“any”类型。,这个错误是因为我们在tsconfig.json中指定了"strict": true,这会开启严格的类型检查,可以通过关闭这个选项来解决,只是我们用 TS 就是要用它的类型检查的,所以正确的做法是给data定义类型.

下面来一一修复错误.

安装styled-components的声明文件

yarn add -D @types/styled-components

修改index.tsx

import React, { FC } from 'react'

// ...

interface PageQuery {

data: {

allMarkdownRemark: {

edges: Array<{

node: {

frontmatter: {

title: string

}

excerpt: string

}

}>

}

}

}

const Home: FC<PageQuery> = ({ data }) => {

const node = data.allMarkdownRemark.edges[0].node

const title = node.frontmatter?.title

const excerpt = node.excerpt

return (

<>

<Title>{title}</Title>

<Content>{excerpt}</Content>

</>

)

}

export default Home

// ...

这时候会出现一个新的错误,在excerpt: string处提示Parsing error: Unexpected token,这是因为 ESLint 还无法识别 TS 的语法,下面来配置 ESLint 支持 TS.

配置 ESLint 支持 TypeScript

安装依赖

yarn add -D @typescript-eslint/parser @typescript-eslint/eslint-plugin

配置.eslintrc.js

module.exports = {

parser: `@typescript-eslint/parser`, // 将解析器从`babel-eslint`替换成`@typescript-eslint/parser`,用以解析 TS 代码

extends: [

`google`,

`eslint:recommended`,

`plugin:@typescript-eslint/recommended`, // 使用 @typescript-eslint/eslint-plugin 推荐配置

`plugin:react/recommended`,

`prettier/@typescript-eslint`, // 禁用 @typescript-eslint/eslint-plugin 中与 prettier 冲突的规则

`plugin:prettier/recommended`,

],

plugins: [

`@typescript-eslint`, // 处理 TS 语法规则

`react`,

`filenames`,

],

// ...

}

.vscode/settings.json中添加配置,让VSCode使用ESLint扩展格式化tstsx文件

// .vscode/settings.json

{

"eslint.format.enable": true,

"[javascript]": {

"editor.defaultFormatter": "dbaeumer.vscode-eslint"

},

"[javascriptreact]": {

"editor.defaultFormatter": "dbaeumer.vscode-eslint"

},

"[typescript]": {

"editor.defaultFormatter": "dbaeumer.vscode-eslint"

},

"[typescriptreact]": {

"editor.defaultFormatter": "dbaeumer.vscode-eslint"

}

}

完善 GraphQL 类型提示

// index.tsx

import React, { FC } from 'react'

// ...

interface PageQuery {

data: {

allMarkdownRemark: {

edges: Array<{

node: {

frontmatter: {

title: string

}

excerpt: string

}

}>

}

}

}

const Home: FC<PageQuery> = ({ data }) => {

// ...

}

export default Home

export const query = graphql`

query {

allMarkdownRemark {

edges {

node {

frontmatter {

title

}

excerpt

}

}

}

}

`

我们看看index.tsx文件,会发现PropTypesquery结构非常类似,在Gatsby运行时,会把query查询的结果作为组件prop.data传入组件,而PropTypes是用来约束prop存在的.所以其实PropTypes就是根据query写出来的.

如果有依据query自动生成PropTypes的功能就太棒了.

另外一个问题是在query中编写GraphQL查询时,并没有类型约束,也没有智能提示.

这两个问题可以通过gatsby-plugin-codegen扩展来解决.

gatsby-plugin-codegen会生成apollo.config.jsschema.json,配合vscode-apollo扩展,可以提供GraphQL的类型约束和智能提示.

另外会自动根据query中的GraphQL查询,生成 TS 类型,放在对应的tsx文件同级目录下的__generated__文件夹,使用时只需要引入即可.

下面是具体操作

安装vscode-apollo扩展

在 VSCode 中按 Ctrl + P ( MAC 下: Cmd + P) 输入以下命令,按回车安装

ext install apollographql.vscode-apollo

安装gatsby-plugin-codegen依赖

在项目中添加依赖

yarn add gatsby-plugin-codegen

配置gatsby-config.js

添加gatsby-plugin-codegen插件

// gatsby-config.js

module.exports = {

plugins: [

// ...

{

resolve: `gatsby-plugin-codegen`,

options: {},

},

],

}

重新运行Gatsby生成类型文件

yarn develop

如果出现以下错误,一般是因为没有为查询命名的缘故,给查询添加命名即可,另外配置正确的话,打开对应的文件,有匿名查询,编辑器会有错误提示.

fix-anonymous-operations.png

这个命名之后会作为生成的类型名.

修改index.tsx以使用生成的类型

gatsby-plugin-codegen插件会更具查询生成对应的查询名称的类型,保存在对应tsx文件同级的__generated__目录下.使用时引入即可.

import { HomeQuery } from './__generated__/HomeQuery' // 引入自动生成的类型

// ...

// interface PageQuery {

// data: {

// allMarkdownRemark: {

// edges: Array<{

// node: {

// frontmatter: {

// title: string

// }

// excerpt: string

// }

// }>

// }

// }

// }

interface PageQuery {

data: HomeQuery // 替换之前手写的类型

}

// ...

将自动生成的文件添加到.gitignore

# Generated types by gatsby-plugin-codegen

__generated__

apollo.config.js

schema.json

扩展阅读

  • 相关资料

    • Gatsby Native TypeScript support
    • Function Components
    • tsconfig.json
    • typescript-eslint
    • gatsby-plugin-codegen
    • Why the TypeScript team is using Gatsby for its new website

  • 类似教程

    • INTRODUCTION: MIGRATING GATSBY SITE TO TYPESCRIPT

以上是 Gatsby项目迁移到TypeScript 的全部内容, 来源链接: utcz.com/a/21094.html

回到顶部