Skip to content

Commit

Permalink
Use async file access (#577)
Browse files Browse the repository at this point in the history
  • Loading branch information
bmish authored Dec 6, 2024
1 parent 0ad8110 commit 84192e3
Show file tree
Hide file tree
Showing 3 changed files with 22 additions and 20 deletions.
2 changes: 1 addition & 1 deletion lib/cli.ts
Original file line number Diff line number Diff line change
Expand Up @@ -186,7 +186,7 @@ export async function run(

// Documentation for options should be kept in sync with README.md and the JSDocs for the `GenerateOptions` type.
await program
.version(getCurrentPackageVersion())
.version(await getCurrentPackageVersion())
.addArgument(
new Argument('[path]', 'path to ESLint plugin root').default('.')
)
Expand Down
19 changes: 10 additions & 9 deletions lib/generator.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { EOL } from 'node:os';
import { existsSync, mkdirSync, readFileSync, writeFileSync } from 'node:fs';
import { existsSync } from 'node:fs';
import { dirname, join, relative, resolve } from 'node:path';
import { getAllNamedOptions, hasOptions } from './rule-options.js';
import {
Expand Down Expand Up @@ -33,6 +33,7 @@ import type { GenerateOptions } from './types.js';
import { OPTION_TYPE, RuleModule } from './types.js';
import { replaceRulePlaceholder } from './rule-link.js';
import { updateRuleOptionsList } from './rule-options-list.js';
import { mkdir, readFile, writeFile } from 'node:fs/promises';

function stringOrArrayWithFallback<T extends string | readonly string[]>(
stringOrArray: undefined | T,
Expand Down Expand Up @@ -63,7 +64,7 @@ function stringOrArrayToArrayWithFallback(
// eslint-disable-next-line complexity
export async function generate(path: string, options?: GenerateOptions) {
const plugin = await loadPlugin(path);
const pluginPrefix = getPluginPrefix(path);
const pluginPrefix = await getPluginPrefix(path);
const configsToRules = await resolveConfigsToRules(plugin);

if (!plugin.rules) {
Expand Down Expand Up @@ -183,8 +184,8 @@ export async function generate(path: string, options?: GenerateOptions) {
newRuleDocContents = `${EOL}${newRuleDocContents}${EOL}`;
}

mkdirSync(dirname(pathToDoc), { recursive: true });
writeFileSync(pathToDoc, newRuleDocContents);
await mkdir(dirname(pathToDoc), { recursive: true });
await writeFile(pathToDoc, newRuleDocContents);
initializedRuleDoc = true;
}

Expand All @@ -206,7 +207,7 @@ export async function generate(path: string, options?: GenerateOptions) {
urlRuleDoc
);

const contentsOld = readFileSync(pathToDoc).toString();
const contentsOld = (await readFile(pathToDoc)).toString(); // eslint-disable-line unicorn/no-await-expression-member
const contentsNew = await postprocess(
updateRuleOptionsList(
replaceOrCreateHeader(
Expand All @@ -231,7 +232,7 @@ export async function generate(path: string, options?: GenerateOptions) {
process.exitCode = 1;
}
} else {
writeFileSync(pathToDoc, contentsNew);
await writeFile(pathToDoc, contentsNew);
}

// Check for potential issues with the rule doc.
Expand Down Expand Up @@ -284,7 +285,7 @@ export async function generate(path: string, options?: GenerateOptions) {

for (const pathRuleListItem of pathRuleList) {
// Find the exact filename.
const pathToFile = getPathWithExactFileNameCasing(
const pathToFile = await getPathWithExactFileNameCasing(
join(path, pathRuleListItem)
);
if (!pathToFile || !existsSync(pathToFile)) {
Expand All @@ -294,7 +295,7 @@ export async function generate(path: string, options?: GenerateOptions) {
}

// Update the rules list in this file.
const fileContents = readFileSync(pathToFile, 'utf8');
const fileContents = await readFile(pathToFile, 'utf8');
const fileContentsNew = await postprocess(
updateConfigsList(
updateRulesList(
Expand Down Expand Up @@ -336,7 +337,7 @@ export async function generate(path: string, options?: GenerateOptions) {
process.exitCode = 1;
}
} else {
writeFileSync(pathToFile, fileContentsNew, 'utf8');
await writeFile(pathToFile, fileContentsNew, 'utf8');
}
}
}
21 changes: 11 additions & 10 deletions lib/package-json.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,26 +6,27 @@ import {
isAbsolute,
extname,
} from 'node:path';
import { existsSync, readFileSync, readdirSync } from 'node:fs';
import { existsSync } from 'node:fs';
import { importAbs } from './import.js';
import { createRequire } from 'node:module';
import type { Plugin } from './types.js';
import type { PackageJson } from 'type-fest';
import { readdir, readFile } from 'node:fs/promises';

const require = createRequire(import.meta.url);

export function getPluginRoot(path: string) {
return isAbsolute(path) ? path : join(process.cwd(), path);
}

function loadPackageJson(path: string): PackageJson {
async function loadPackageJson(path: string): Promise<PackageJson> {
const pluginRoot = getPluginRoot(path);
const pluginPackageJsonPath = join(pluginRoot, 'package.json');
if (!existsSync(pluginPackageJsonPath)) {
throw new Error('Could not find package.json of ESLint plugin.');
}
const pluginPackageJson = JSON.parse(
readFileSync(join(pluginRoot, 'package.json'), 'utf8')
await readFile(join(pluginRoot, 'package.json'), 'utf8')
) as PackageJson;

return pluginPackageJson;
Expand All @@ -38,7 +39,7 @@ export async function loadPlugin(path: string): Promise<Plugin> {
return require(pluginRoot) as Plugin; // eslint-disable-line import/no-dynamic-require
} catch (error) {
// Otherwise, for ESM plugins, we'll have to try to resolve the exact plugin entry point and import it.
const pluginPackageJson = loadPackageJson(path);
const pluginPackageJson = await loadPackageJson(path);
let pluginEntryPoint;
const exports = pluginPackageJson.exports;
if (typeof exports === 'string') {
Expand Down Expand Up @@ -88,8 +89,8 @@ export async function loadPlugin(path: string): Promise<Plugin> {
}
}

export function getPluginPrefix(path: string): string {
const pluginPackageJson = loadPackageJson(path);
export async function getPluginPrefix(path: string): Promise<string> {
const pluginPackageJson = await loadPackageJson(path);
if (!pluginPackageJson.name) {
throw new Error(
"Could not find `name` field in ESLint plugin's package.json."
Expand All @@ -103,10 +104,10 @@ export function getPluginPrefix(path: string): string {
/**
* Resolve the path to a file but with the exact filename-casing present on disk.
*/
export function getPathWithExactFileNameCasing(path: string) {
export async function getPathWithExactFileNameCasing(path: string) {
const dir = dirname(path);
const fileNameToSearch = basename(path);
const filenames = readdirSync(dir, { withFileTypes: true });
const filenames = await readdir(dir, { withFileTypes: true });
for (const dirent of filenames) {
if (
dirent.isFile() &&
Expand All @@ -118,15 +119,15 @@ export function getPathWithExactFileNameCasing(path: string) {
return undefined; // eslint-disable-line unicorn/no-useless-undefined
}

export function getCurrentPackageVersion(): string {
export async function getCurrentPackageVersion(): Promise<string> {
// When running as compiled code, use path relative to compiled version of this file in the dist folder.
// When running as TypeScript (in a test), use path relative to this file.
const pathToPackageJson = import.meta.url.endsWith('.ts')
? '../package.json'
: /* istanbul ignore next -- can't test the compiled version in test */
'../../package.json';
const packageJson = JSON.parse(
readFileSync(new URL(pathToPackageJson, import.meta.url), 'utf8')
await readFile(new URL(pathToPackageJson, import.meta.url), 'utf8')
) as PackageJson;
if (!packageJson.version) {
throw new Error('Could not find package.json `version`.');
Expand Down

0 comments on commit 84192e3

Please sign in to comment.