refactor: remove a few Lodash usages & ESLint enforcement (#5807)

* refactor: remove some lodash usage

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* Enforce ESLint

Signed-off-by: Josh-Cena <sidachen2003@gmail.com>

* More forbids

* Fixup

* Fix

* Fix website
This commit is contained in:
Joshua Chen 2021-10-28 12:48:58 +08:00 committed by GitHub
parent 4b2152a964
commit 7a6607cfa1
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
12 changed files with 60 additions and 49 deletions

View file

@ -129,11 +129,36 @@ module.exports = {
'no-redeclare': OFF, 'no-redeclare': OFF,
'@typescript-eslint/no-redeclare': ERROR, '@typescript-eslint/no-redeclare': ERROR,
'@typescript-eslint/no-empty-interface': [ '@typescript-eslint/no-empty-interface': [
'error', ERROR,
{ {
allowSingleExtends: true, allowSingleExtends: true,
}, },
], ],
'no-restricted-imports': [
ERROR,
{
paths: [
{
name: 'lodash',
importNames: [
// 'compact', // TODO: TS doesn't make Boolean a narrowing function yet, so filter(Boolean) is problematic type-wise
'filter',
'flatten',
'flatMap',
'map',
'reduce',
'take',
'takeRight',
'head',
'tail',
'initial',
'last',
],
message: 'These APIs have their ES counterparts.',
},
],
},
],
}, },
overrides: [ overrides: [
{ {

View file

@ -5,7 +5,7 @@
* LICENSE file in the root directory of this source tree. * LICENSE file in the root directory of this source tree.
*/ */
import {flatten, uniqBy, difference, groupBy} from 'lodash'; import {uniqBy, difference, groupBy} from 'lodash';
import { import {
PluginContext, PluginContext,
RedirectMetadata, RedirectMetadata,
@ -165,7 +165,7 @@ function createRedirectsOptionRedirects(
})); }));
} }
return flatten(redirectsOption.map(optionToRedirects)); return redirectsOption.flatMap(optionToRedirects);
} }
// Create redirects from the "createRedirects" fn provided by the user // Create redirects from the "createRedirects" fn provided by the user
@ -189,5 +189,5 @@ function createCreateRedirectsOptionRedirects(
}); });
} }
return flatten(paths.map(createPathRedirects)); return paths.flatMap(createPathRedirects);
} }

View file

@ -5,7 +5,6 @@
* LICENSE file in the root directory of this source tree. * LICENSE file in the root directory of this source tree.
*/ */
import {flatten} from 'lodash';
import { import {
addTrailingSlash, addTrailingSlash,
removeSuffix, removeSuffix,
@ -62,7 +61,7 @@ export function createToExtensionsRedirects(
return []; return [];
}; };
return flatten(paths.map(createPathRedirects)); return paths.flatMap(createPathRedirects);
} }
// Create new /path.html/index.html that redirects to existing an /path // Create new /path.html/index.html that redirects to existing an /path
@ -99,5 +98,5 @@ export function createFromExtensionsRedirects(
})); }));
}; };
return flatten(paths.map(createPathRedirects)); return paths.flatMap(createPathRedirects);
} }

View file

@ -9,7 +9,7 @@ import fs from 'fs-extra';
import chalk from 'chalk'; import chalk from 'chalk';
import path from 'path'; import path from 'path';
import readingTime from 'reading-time'; import readingTime from 'reading-time';
import {compact, keyBy, mapValues} from 'lodash'; import {keyBy, mapValues} from 'lodash';
import { import {
PluginOptions, PluginOptions,
BlogPost, BlogPost,
@ -267,7 +267,7 @@ export async function generateBlogPosts(
authorsMapPath: options.authorsMapPath, authorsMapPath: options.authorsMapPath,
}); });
const blogPosts: BlogPost[] = compact( const blogPosts = (
await Promise.all( await Promise.all(
blogSourceFiles.map(async (blogSourceFile: string) => { blogSourceFiles.map(async (blogSourceFile: string) => {
try { try {
@ -287,8 +287,8 @@ export async function generateBlogPosts(
throw e; throw e;
} }
}), }),
), )
); ).filter(Boolean) as BlogPost[];
blogPosts.sort( blogPosts.sort(
(a, b) => b.metadata.date.getTime() - a.metadata.date.getTime(), (a, b) => b.metadata.date.getTime() - a.metadata.date.getTime(),

View file

@ -22,7 +22,6 @@ import {
DEFAULT_PLUGIN_ID, DEFAULT_PLUGIN_ID,
} from '@docusaurus/core/lib/constants'; } from '@docusaurus/core/lib/constants';
import {translateContent, getTranslationFiles} from './translations'; import {translateContent, getTranslationFiles} from './translations';
import {flatten, take} from 'lodash';
import { import {
PluginOptions, PluginOptions,
@ -98,10 +97,8 @@ export default function pluginContentBlog(
getPathsToWatch() { getPathsToWatch() {
const {include, authorsMapPath} = options; const {include, authorsMapPath} = options;
const contentMarkdownGlobs = flatten( const contentMarkdownGlobs = getContentPathList(contentPaths).flatMap(
getContentPathList(contentPaths).map((contentPath) => { (contentPath) => include.map((pattern) => `${contentPath}/${pattern}`),
return include.map((pattern) => `${contentPath}/${pattern}`);
}),
); );
// TODO: we should read this path in plugin! but plugins do not support async init for now :'( // TODO: we should read this path in plugin! but plugins do not support async init for now :'(
@ -244,7 +241,7 @@ export default function pluginContentBlog(
const sidebarBlogPosts = const sidebarBlogPosts =
options.blogSidebarCount === 'ALL' options.blogSidebarCount === 'ALL'
? blogPosts ? blogPosts
: take(blogPosts, options.blogSidebarCount); : blogPosts.slice(0, options.blogSidebarCount);
const archiveUrl = normalizeUrl([ const archiveUrl = normalizeUrl([
baseUrl, baseUrl,

View file

@ -42,7 +42,7 @@ import {
import {RuleSetRule} from 'webpack'; import {RuleSetRule} from 'webpack';
import {cliDocsVersionCommand} from './cli'; import {cliDocsVersionCommand} from './cli';
import {VERSIONS_JSON_FILE} from './constants'; import {VERSIONS_JSON_FILE} from './constants';
import {keyBy, compact, mapValues} from 'lodash'; import {keyBy, mapValues} from 'lodash';
import {toGlobalDataVersion} from './globalData'; import {toGlobalDataVersion} from './globalData';
import {toTagDocListProp, toVersionMetadataProp} from './props'; import {toTagDocListProp, toVersionMetadataProp} from './props';
import { import {
@ -388,7 +388,7 @@ export default function pluginContentDocs(
include: contentDirs include: contentDirs
// Trailing slash is important, see https://github.com/facebook/docusaurus/pull/3970 // Trailing slash is important, see https://github.com/facebook/docusaurus/pull/3970
.map(addTrailingPathSeparator), .map(addTrailingPathSeparator),
use: compact([ use: [
getJSLoader({isServer}), getJSLoader({isServer}),
{ {
loader: require.resolve('@docusaurus/mdx-loader'), loader: require.resolve('@docusaurus/mdx-loader'),
@ -414,7 +414,7 @@ export default function pluginContentDocs(
loader: path.resolve(__dirname, './markdown/index.js'), loader: path.resolve(__dirname, './markdown/index.js'),
options: docsMarkdownOptions, options: docsMarkdownOptions,
}, },
]), ].filter(Boolean),
}; };
} }

View file

@ -40,7 +40,6 @@ import {
Metadata, Metadata,
PagesContentPaths, PagesContentPaths,
} from './types'; } from './types';
import {flatten} from 'lodash';
export function getContentPathList(contentPaths: PagesContentPaths): string[] { export function getContentPathList(contentPaths: PagesContentPaths): string[] {
return [contentPaths.contentPathLocalized, contentPaths.contentPath]; return [contentPaths.contentPathLocalized, contentPaths.contentPath];
@ -86,10 +85,8 @@ export default function pluginContentPages(
getPathsToWatch() { getPathsToWatch() {
const {include = []} = options; const {include = []} = options;
return flatten( return getContentPathList(contentPaths).flatMap((contentPath) =>
getContentPathList(contentPaths).map((contentPath) => { include.map((pattern) => `${contentPath}/${pattern}`),
return include.map((pattern) => `${contentPath}/${pattern}`);
}),
); );
}, },

View file

@ -13,18 +13,16 @@ import {
Footer, Footer,
} from '@docusaurus/theme-common'; } from '@docusaurus/theme-common';
import {keyBy, chain, flatten} from 'lodash'; import {keyBy, chain} from 'lodash';
import {mergeTranslations} from '@docusaurus/utils'; import {mergeTranslations} from '@docusaurus/utils';
function getNavbarTranslationFile(navbar: Navbar): TranslationFileContent { function getNavbarTranslationFile(navbar: Navbar): TranslationFileContent {
// TODO handle properly all the navbar item types here! // TODO handle properly all the navbar item types here!
function flattenNavbarItems(items: NavbarItem[]): NavbarItem[] { function flattenNavbarItems(items: NavbarItem[]): NavbarItem[] {
const subItems = flatten( const subItems = items.flatMap((item) => {
items.map((item) => { const allSubItems = [item.items ?? []].flat();
const allSubItems = flatten([item.items ?? []]);
return flattenNavbarItems(allSubItems); return flattenNavbarItems(allSubItems);
}), });
);
return [...items, ...subItems]; return [...items, ...subItems];
} }
@ -84,9 +82,7 @@ function getFooterTranslationFile(footer: Footer): TranslationFileContent {
.value(); .value();
const footerLinkLabels: TranslationFileContent = chain( const footerLinkLabels: TranslationFileContent = chain(
flatten(footer.links.map((link) => link.items)).filter( footer.links.flatMap((link) => link.items).filter((link) => !!link.label),
(link) => !!link.label,
),
) )
.keyBy((linkItem) => `link.item.label.${linkItem.label}`) .keyBy((linkItem) => `link.item.label.${linkItem.label}`)
.mapValues((linkItem) => ({ .mapValues((linkItem) => ({

View file

@ -8,7 +8,7 @@
import {matchRoutes, RouteConfig as RRRouteConfig} from 'react-router-config'; import {matchRoutes, RouteConfig as RRRouteConfig} from 'react-router-config';
import resolvePathname from 'resolve-pathname'; import resolvePathname from 'resolve-pathname';
import fs from 'fs-extra'; import fs from 'fs-extra';
import {mapValues, pickBy, flatten, countBy} from 'lodash'; import {mapValues, pickBy, countBy} from 'lodash';
import {RouteConfig, ReportingSeverity} from '@docusaurus/types'; import {RouteConfig, ReportingSeverity} from '@docusaurus/types';
import {removePrefix, removeSuffix, reportMessage} from '@docusaurus/utils'; import {removePrefix, removeSuffix, reportMessage} from '@docusaurus/utils';
import {getAllFinalRoutes} from './utils'; import {getAllFinalRoutes} from './utils';
@ -110,10 +110,9 @@ export function getBrokenLinksErrorMessage(
// Add an additional message in such case to help user figure this out. // Add an additional message in such case to help user figure this out.
// see https://github.com/facebook/docusaurus/issues/3567#issuecomment-706973805 // see https://github.com/facebook/docusaurus/issues/3567#issuecomment-706973805
function getLayoutBrokenLinksHelpMessage() { function getLayoutBrokenLinksHelpMessage() {
const flatList = flatten( const flatList = Object.entries(allBrokenLinks).flatMap(
Object.entries(allBrokenLinks).map(([pagePage, brokenLinks]) => ([pagePage, brokenLinks]) =>
brokenLinks.map((brokenLink) => ({pagePage, brokenLink})), brokenLinks.map((brokenLink) => ({pagePage, brokenLink})),
),
); );
const countedBrokenLinks = countBy( const countedBrokenLinks = countBy(

View file

@ -9,7 +9,6 @@ import traverse, {Node} from '@babel/traverse';
import generate from '@babel/generator'; import generate from '@babel/generator';
import chalk from 'chalk'; import chalk from 'chalk';
import {parse, types as t, NodePath, TransformOptions} from '@babel/core'; import {parse, types as t, NodePath, TransformOptions} from '@babel/core';
import {flatten} from 'lodash';
import { import {
InitializedPlugin, InitializedPlugin,
TranslationFileContent, TranslationFileContent,
@ -69,7 +68,7 @@ async function getSourceCodeFilePaths(
// The getPathsToWatch() generally returns the js/jsx/ts/tsx/md/mdx file paths // The getPathsToWatch() generally returns the js/jsx/ts/tsx/md/mdx file paths
// We can use this method as well to know which folders we should try to extract translations from // We can use this method as well to know which folders we should try to extract translations from
// Hacky/implicit, but do we want to introduce a new lifecycle method for that??? // Hacky/implicit, but do we want to introduce a new lifecycle method for that???
const pluginsPaths = flatten(plugins.map(getPluginSourceCodeFilePaths)); const pluginsPaths = plugins.flatMap(getPluginSourceCodeFilePaths);
const allPaths = [...sitePaths, ...pluginsPaths]; const allPaths = [...sitePaths, ...pluginsPaths];
@ -133,12 +132,10 @@ export async function extractAllSourceCodeFileTranslations(
sourceCodeFilePaths: string[], sourceCodeFilePaths: string[],
babelOptions: TransformOptions, babelOptions: TransformOptions,
): Promise<SourceCodeFileTranslations[]> { ): Promise<SourceCodeFileTranslations[]> {
return flatten( return Promise.all(
await Promise.all( sourceCodeFilePaths.flatMap((sourceFilePath) =>
sourceCodeFilePaths.map((sourceFilePath) =>
extractSourceCodeFileTranslations(sourceFilePath, babelOptions), extractSourceCodeFileTranslations(sourceFilePath, babelOptions),
), ),
),
); );
} }

View file

@ -4,7 +4,7 @@
* This source code is licensed under the MIT license found in the * This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree. * LICENSE file in the root directory of this source tree.
*/ */
import {flatMap} from 'lodash';
import {RouteConfig} from '@docusaurus/types'; import {RouteConfig} from '@docusaurus/types';
import nodePath from 'path'; import nodePath from 'path';
import {posixPath, Globby} from '@docusaurus/utils'; import {posixPath, Globby} from '@docusaurus/utils';
@ -12,9 +12,9 @@ import {posixPath, Globby} from '@docusaurus/utils';
// Recursively get the final routes (routes with no subroutes) // Recursively get the final routes (routes with no subroutes)
export function getAllFinalRoutes(routeConfig: RouteConfig[]): RouteConfig[] { export function getAllFinalRoutes(routeConfig: RouteConfig[]): RouteConfig[] {
function getFinalRoutes(route: RouteConfig): RouteConfig[] { function getFinalRoutes(route: RouteConfig): RouteConfig[] {
return route.routes ? flatMap(route.routes, getFinalRoutes) : [route]; return route.routes ? route.routes.flatMap(getFinalRoutes) : [route];
} }
return flatMap(routeConfig, getFinalRoutes); return routeConfig.flatMap(getFinalRoutes);
} }
// Globby that fix Windows path patterns // Globby that fix Windows path patterns

View file

@ -2,6 +2,7 @@
// This file is not used in compilation. It is here just for a nice editor experience. // This file is not used in compilation. It is here just for a nice editor experience.
"extends": "@tsconfig/docusaurus/tsconfig.json", "extends": "@tsconfig/docusaurus/tsconfig.json",
"compilerOptions": { "compilerOptions": {
"lib": ["DOM", "ESNext"],
"baseUrl": ".", "baseUrl": ".",
"resolveJsonModule": true "resolveJsonModule": true
}, },