Skip to content

Commit 6140b5a

Browse files
committed
[migrate] upgrade React, ESLint configuration & other Upstream packages
[fix] some detail bugs
1 parent 25a1685 commit 6140b5a

File tree

13 files changed

+1943
-895
lines changed

13 files changed

+1943
-895
lines changed

.github/workflows/main.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ name: CI & CD
22
on:
33
push:
44
branches:
5-
- '*'
5+
- '**'
66
jobs:
77
Build-and-Deploy:
88
env:

components/Form/BlockEditor.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ async function uploadByFile(file: File) {
1515
return { success: 1, file: { url } };
1616
} catch (error) {
1717
console.error(error);
18+
1819
return { success: 0 };
1920
}
2021
}

components/Layout/NotFoundCard.tsx

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
11
import { ErrorProps } from 'next/error';
2+
import Script from 'next/script';
23
import { FC } from 'react';
34

45
import { i18n } from '../../models/Translation';
56

67
export const NotFoundCard: FC<ErrorProps> = ({ title }) =>
78
i18n.currentLanguage.startsWith('zh') ? (
8-
<script
9+
<Script
910
src="//cdn.dnpw.org/404/v1.min.js"
1011
// @ts-expect-error https://www.dnpw.org/cn/pa-notfound.html
1112
jumptarget="/"

components/Layout/PageHead.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ export const PageHead: FC<PageHeadProps> = ({
1515
children,
1616
}) => (
1717
<Head>
18-
<title>{`${title}${title && ' - '}${Name}`}</title>
18+
<title>{`${title}${title ? ' - ' : ''}${Name}`}</title>
1919

2020
{description && <meta name="description" content={description} />}
2121

eslint.config.mjs

Lines changed: 71 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,24 +1,32 @@
1-
// @ts-check
2-
import { fixupPluginRules } from '@eslint/compat';
3-
import { FlatCompat } from '@eslint/eslintrc';
1+
import cspellPlugin from '@cspell/eslint-plugin';
42
import eslint from '@eslint/js';
3+
// @ts-expect-error eslint-plugin-next doesn't come with TypeScript definitions
4+
import nextPlugin from '@next/eslint-plugin-next';
5+
import stylistic from '@stylistic/eslint-plugin';
56
import eslintConfigPrettier from 'eslint-config-prettier';
6-
import reactPlugin from 'eslint-plugin-react';
7+
import react from 'eslint-plugin-react';
78
import simpleImportSortPlugin from 'eslint-plugin-simple-import-sort';
89
import globals from 'globals';
910
import tsEslint from 'typescript-eslint';
1011
import { fileURLToPath } from 'url';
1112

12-
const tsconfigRootDir = fileURLToPath(new URL('.', import.meta.url)),
13-
flatCompat = new FlatCompat();
13+
/**
14+
* @see{@link https://github.com/typescript-eslint/typescript-eslint/blob/main/eslint.config.mjs}
15+
* @see{@link https://github.com/vercel/next.js/issues/71763#issuecomment-2476838298}
16+
*/
17+
18+
const tsconfigRootDir = fileURLToPath(new URL('.', import.meta.url));
1419

1520
export default tsEslint.config(
1621
// register all of the plugins up-front
1722
{
1823
plugins: {
19-
'@typescript-eslint': tsEslint.plugin,
20-
react: fixupPluginRules(reactPlugin),
24+
'@cspell': cspellPlugin,
25+
'@stylistic': stylistic,
2126
'simple-import-sort': simpleImportSortPlugin,
27+
'@typescript-eslint': tsEslint.plugin,
28+
react,
29+
'@next/next': nextPlugin,
2230
},
2331
},
2432
{
@@ -34,7 +42,6 @@ export default tsEslint.config(
3442
// extends ...
3543
eslint.configs.recommended,
3644
...tsEslint.configs.recommended,
37-
...flatCompat.extends('plugin:@next/next/core-web-vitals'),
3845

3946
// base config
4047
{
@@ -47,13 +54,65 @@ export default tsEslint.config(
4754
},
4855
},
4956
rules: {
57+
// spellchecker
58+
'@cspell/spellchecker': [
59+
'warn',
60+
{
61+
cspell: {
62+
language: 'en',
63+
dictionaries: [
64+
'typescript',
65+
'node',
66+
'html',
67+
'css',
68+
'bash',
69+
'npm',
70+
'pnpm',
71+
],
72+
},
73+
},
74+
],
75+
// stylistic
76+
'@stylistic/padding-line-between-statements': [
77+
'error',
78+
{ blankLine: 'always', prev: '*', next: 'return' },
79+
{ blankLine: 'always', prev: 'directive', next: '*' },
80+
{ blankLine: 'any', prev: 'directive', next: 'directive' },
81+
{
82+
blankLine: 'always',
83+
prev: '*',
84+
next: ['enum', 'interface', 'type'],
85+
},
86+
],
87+
'arrow-body-style': ['error', 'as-needed'],
5088
'no-empty-pattern': 'warn',
89+
'no-console': ['error', { allow: ['warn', 'error', 'info'] }],
90+
'no-restricted-syntax': [
91+
'error',
92+
{
93+
selector: "TSPropertySignature[key.name='children']",
94+
message:
95+
'Please use PropsWithChildren<T> instead of defining children manually',
96+
},
97+
],
98+
'consistent-return': 'warn',
99+
'prefer-destructuring': ['error', { object: true, array: true }],
100+
// simple-import-sort
51101
'simple-import-sort/exports': 'error',
52102
'simple-import-sort/imports': 'error',
103+
// TypeScript
53104
'@typescript-eslint/no-unused-vars': 'warn',
54105
'@typescript-eslint/no-explicit-any': 'warn',
55106
'@typescript-eslint/no-empty-object-type': 'off',
56107
'@typescript-eslint/no-unsafe-declaration-merging': 'warn',
108+
'@typescript-eslint/consistent-type-definitions': ['error', 'interface'],
109+
// React
110+
'react/no-unescaped-entities': 'off',
111+
'react/self-closing-comp': ['error', { component: true, html: true }],
112+
'react/jsx-curly-brace-presence': [
113+
'error',
114+
{ props: 'never', children: 'never' },
115+
],
57116
'react/jsx-no-target-blank': 'warn',
58117
'react/jsx-sort-props': [
59118
'error',
@@ -63,19 +122,11 @@ export default tsEslint.config(
63122
noSortAlphabetically: true,
64123
},
65124
],
125+
// Next.js
126+
...nextPlugin.configs.recommended.rules,
127+
...nextPlugin.configs['core-web-vitals'].rules,
66128
'@next/next/no-sync-scripts': 'warn',
67129
},
68130
},
69-
{
70-
files: ['**/*.js'],
71-
extends: [tsEslint.configs.disableTypeChecked],
72-
rules: {
73-
// turn off other type-aware rules
74-
'@typescript-eslint/internal/no-poorly-typed-ts-props': 'off',
75-
76-
// turn off rules that don't apply to JS code
77-
'@typescript-eslint/explicit-function-return-type': 'off',
78-
},
79-
},
80131
eslintConfigPrettier,
81132
);

package.json

Lines changed: 21 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -17,12 +17,12 @@
1717
"@editorjs/quote": "~2.7.6",
1818
"@mdx-js/loader": "^3.1.0",
1919
"@mdx-js/react": "^3.1.0",
20-
"@next/mdx": "^15.2.1",
21-
"@sentry/nextjs": "^9.4.0",
20+
"@next/mdx": "^15.2.2",
21+
"@sentry/nextjs": "^9.5.0",
2222
"copy-webpack-plugin": "^13.0.0",
2323
"core-js": "^3.41.0",
2424
"editorjs-html": "^4.0.5",
25-
"file-type": "^20.4.0",
25+
"file-type": "^20.4.1",
2626
"idea-react": "^2.0.0-rc.8",
2727
"koajax": "^3.1.1",
2828
"less": "^4.2.2",
@@ -36,49 +36,51 @@
3636
"mobx-lark": "^2.0.0",
3737
"mobx-react": "^9.2.0",
3838
"mobx-restful": "^2.1.0",
39-
"mobx-restful-table": "^2.0.1",
40-
"next": "^15.2.1",
39+
"mobx-restful-table": "^2.0.2",
40+
"next": "^15.2.2",
4141
"next-pwa": "~5.6.0",
4242
"next-ssr-middleware": "^0.8.9",
4343
"next-with-less": "^3.0.1",
44-
"prismjs": "^1.29.0",
45-
"react": "^18.3.1",
44+
"prismjs": "^1.30.0",
45+
"react": "^19.0.0",
4646
"react-bootstrap": "^2.10.9",
47-
"react-bootstrap-editor": "^2.0.4",
48-
"react-dom": "^18.3.1",
47+
"react-bootstrap-editor": "^2.0.7",
48+
"react-dom": "^19.0.0",
4949
"react-editor-js": "^2.1.0",
5050
"remark-frontmatter": "^5.0.0",
5151
"remark-gfm": "^4.0.1",
5252
"remark-mdx-frontmatter": "^5.0.0",
53-
"undici": "^7.4.0",
53+
"undici": "^7.5.0",
5454
"web-utility": "^4.4.3",
5555
"webpack": "^5.98.0"
5656
},
5757
"devDependencies": {
5858
"@babel/plugin-proposal-decorators": "^7.25.9",
5959
"@babel/plugin-transform-typescript": "^7.26.8",
6060
"@babel/preset-react": "^7.26.3",
61+
"@cspell/eslint-plugin": "^8.17.5",
6162
"@eslint/compat": "^1.2.7",
6263
"@eslint/eslintrc": "^3.3.0",
63-
"@eslint/js": "^9.21.0",
64+
"@eslint/js": "^9.22.0",
6465
"@softonus/prettier-plugin-duplicate-remover": "^1.1.2",
66+
"@stylistic/eslint-plugin": "^4.2.0",
6567
"@types/eslint-config-prettier": "^6.11.3",
6668
"@types/lodash": "^4.17.16",
6769
"@types/next-pwa": "^5.6.9",
68-
"@types/node": "^22.13.9",
69-
"@types/react": "^18.3.18",
70-
"eslint": "^9.21.0",
71-
"eslint-config-next": "^15.2.1",
72-
"eslint-config-prettier": "^10.0.2",
70+
"@types/node": "^22.13.10",
71+
"@types/react": "^19.0.10",
72+
"eslint": "^9.22.0",
73+
"eslint-config-next": "^15.2.2",
74+
"eslint-config-prettier": "^10.1.1",
7375
"eslint-plugin-react": "^7.37.4",
7476
"eslint-plugin-simple-import-sort": "^12.1.1",
7577
"globals": "^16.0.0",
7678
"husky": "^9.1.7",
77-
"lint-staged": "^15.4.3",
79+
"lint-staged": "^15.5.0",
7880
"prettier": "^3.5.3",
7981
"prettier-plugin-css-order": "^2.1.2",
8082
"typescript": "~5.8.2",
81-
"typescript-eslint": "^8.26.0"
83+
"typescript-eslint": "^8.26.1"
8284
},
8385
"resolutions": {
8486
"next": "$next"
@@ -101,7 +103,7 @@
101103
"dev": "next dev",
102104
"build": "next build",
103105
"start": "next start",
104-
"lint": "next lint && tsc --noEmit",
106+
"lint": "next lint --fix && tsc --noEmit",
105107
"test": "lint-staged && npm run lint",
106108
"pack-image": "docker build -t idea2app/lark-next-bootstrap-ts:latest .",
107109
"container": "docker rm -f lark-next-bootstrap-ts && docker run --name lark-next-bootstrap-ts -p 3000:3000 -d idea2app/lark-next-bootstrap-ts:latest"

pages/_document.tsx

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import { Head, Html, Main, NextScript } from 'next/document';
2+
import Script from 'next/script';
23

34
export default function Document() {
45
return (
@@ -7,7 +8,7 @@ export default function Document() {
78
<link rel="icon" href="/favicon.ico" />
89

910
<link rel="manifest" href="/manifest.json" />
10-
<script src="https://polyfill.web-cell.dev/feature/PWAManifest.js"></script>
11+
<Script src="https://polyfill.web-cell.dev/feature/PWAManifest.js" />
1112

1213
<link
1314
rel="stylesheet"

pages/api/Lark/bitable/v1/[...slug].ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,5 +21,6 @@ export default proxyLark((URI, data) => {
2121

2222
filterData(record.fields);
2323
}
24+
2425
return data;
2526
});

pages/api/core.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ export function safeAPI(handler: NextAPI): NextAPI {
2020
console.error(error);
2121

2222
res.status(400);
23+
2324
return res.send({ message: (error as Error).message });
2425
}
2526
const { message, response } = error;

pages/api/hello.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,9 @@ import type { NextApiResponse } from 'next';
33

44
import { safeAPI } from './core';
55

6-
type Data = {
6+
interface Data {
77
name: string;
8-
};
8+
}
99

1010
export default safeAPI(async (req, res: NextApiResponse<Data>) =>
1111
res.status(401).json({ name: 'John Doe' }),

0 commit comments

Comments
 (0)