8000 fix(docutils): add & adjust various log messages by eglitise · Pull Request #21160 · appium/appium · GitHub
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content

fix(docutils): add & adjust various log messages #21160

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Apr 2, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 7 additions & 8 deletions packages/docutils/lib/builder/deploy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,9 @@ import {
NAME_BIN,
NAME_MIKE,
NAME_MKDOCS_YML,
NAME_PYTHON,
} from '../constants';
import {DocutilsError} from '../error';
import {findMike, findMkDocsYml, findPython, readPackageJson} from '../fs';
import {findMike, findMkDocsYml, isMkDocsInstalled, readPackageJson, requirePython} from '../fs';
import {getLogger} from '../logger';
import {argify, spawnBackgroundProcess, SpawnBackgroundProcessOpts, stopwatch} from '../util';

Expand All @@ -37,6 +36,7 @@ async function doServe(
opts: SpawnBackgroundProcessOpts = {},
) {
const finalArgs = ['serve', ...args];
log.debug('Executing %s via: %s %O', NAME_MIKE, mikePath, finalArgs);
return spawnBackgroundProcess(mikePath, finalArgs, opts);
}

Expand Down Expand Up @@ -99,18 +99,17 @@ export async function deploy({
}: DeployOpts = {}) {
const stop = stopwatch('deploy');

const pythonPath = await findPython();
await requirePython();

if (!pythonPath) {
throw new DocutilsError(
`Could not find ${NAME_PYTHON}3/${NAME_PYTHON} executable in PATH; please install Python v3`,
);
const mkdocsInstalled = await isMkDocsInstalled();
if (!mkdocsInstalled) {
throw new DocutilsError(`Could not find MkDocs executable; please run "${NAME_BIN} init"`);
}

mkDocsYmlPath = mkDocsYmlPath ?? (await findMkDocsYml(cwd));
if (!mkDocsYmlPath) {
throw new DocutilsError(
`Could not find ${NAME_MKDOCS_YML} from ${cwd}; run "${NAME_BIN} init" to create it`,
`Could not find ${NAME_MKDOCS_YML} from ${cwd}; please run "${NAME_BIN} init"`,
);
}
version = version ?? (await findDeployVersion(packageJsonPath, cwd));
Expand Down
16 changes: 8 additions & 8 deletions packages/docutils/lib/builder/site.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,9 @@

import path from 'node:path';
import {exec, TeenProcessExecOptions} from 'teen_process';
import {DEFAULT_SITE_DIR, NAME_BIN, NAME_MKDOCS, NAME_MKDOCS_YML, NAME_PYTHON} from '../constants';
import {DEFAULT_SITE_DIR, NAME_BIN, NAME_MKDOCS, NAME_MKDOCS_YML} from '../constants';
import {DocutilsError} from '../error';
import {findMkDocsYml, findPython, readMkDocsYml} from '../fs';
import {findMkDocsYml, isMkDocsInstalled, readMkDocsYml, requirePython} from '../fs';
import {getLogger} from '../logger';
import {relative, spawnBackgroundProcess, SpawnBackgroundProcessOpts, stopwatch} from '../util';

Expand Down Expand Up @@ -58,19 +58,19 @@ export async function buildSite({
}: BuildMkDocsOpts = {}) {
const stop = stopwatch('build-mkdocs');

const pythonPath = await findPython();
if (!pythonPath) {
throw new DocutilsError(
`Could not find ${NAME_PYTHON}3/${NAME_PYTHON} executable in PATH; please install Python v3`,
);
const pythonPath = await requirePython();

const mkdocsInstalled = await isMkDocsInstalled();
if (!mkdocsInstalled) {
throw new DocutilsError(`Could not find MkDocs executable; please run "${NAME_BIN} init"`);
}

mkDocsYmlPath = mkDocsYmlPath
? path.resolve(process.cwd(), mkDocsYmlPath)
: await findMkDocsYml(cwd);
if (!mkDocsYmlPath) {
throw new DocutilsError(
`Could not find ${NAME_MKDOCS_YML} from ${cwd}; run "${NAME_BIN} init" to create it`,
`Could not find ${NAME_MKDOCS_YML} from ${cwd}; please run "${NAME_BIN} init"`,
);
}
const mkdocsArgs = ['-f', mkDocsYmlPath];
Expand Down
10 changes: 5 additions & 5 deletions packages/docutils/lib/constants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -73,11 +73,6 @@ export const NAME_TYPESCRIPT = 'typescript';
*/
export const NAME_ERR_ENOENT = 'ENOENT';

/**
* Code for a "file already exists" error
*/
export const NAME_ERR_EEXIST = 'EEXIST';

/**
* Name of the default theme
*/
Expand Down Expand Up @@ -153,3 +148,8 @@ export const DEFAULT_SITE_DIR = 'site';
* To ensure backwards compatibility, its environment variable version is used
*/
export const PIP_ENV_VARS = {PIP_BREAK_SYSTEM_PACKAGES: '1'};

/**
* Error message emitted when the path to Python was not found
*/
export const MESSAGE_PYTHON_MISSING = 'Could not find Python in PATH. Is it installed?';
51 changes: 44 additions & 7 deletions packages/docutils/lib/fs.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,15 @@ import _pkgDir from 'pkg-dir';
import readPkg, {NormalizedPackageJson, PackageJson} from 'read-pkg';
import {JsonValue} from 'type-fest';
import YAML from 'yaml';
import {NAME_MIKE, NAME_MKDOCS_YML, NAME_NPM, NAME_PACKAGE_JSON, NAME_PYTHON} from './constants';
import {
MESSAGE_PYTHON_MISSING,
NAME_MIKE,
NAME_MKDOCS,
NAME_MKDOCS_YML,
NAME_NPM,
NAME_PACKAGE_JSON,
NAME_PYTHON,
} from './constants';
import {DocutilsError} from './error';
import {getLogger} from './logger';
import {MkDocsYml} from './model';
Expand Down Expand Up @@ -152,18 +160,14 @@ export const readJson = _.memoize(
);

/**
* Writes a file, but will not overwrite an existing file unless `overwrite` is true
*
* Will stringify JSON objects
* Writes contents to a file. Any JSON objects are stringified
* @param filepath - Path to file
* @param content - File contents
* @param overwrite - If `true`, overwrite existing files
*/
export function safeWriteFile(filepath: string, content: JsonValue, overwrite = false) {
export function writeFileString(filepath: string, content: JsonValue) {
const data: string = _.isString(content) ? content : JSON.stringify(content, undefined, 2);
return fs.writeFile(filepath, data, {
encoding: 'utf8',
flag: overwrite ? 'w' : 'wx',
});
}

Expand All @@ -189,6 +193,28 @@ const whichPython = _.partial(cachedWhich, NAME_PYTHON, {nothrow: true});
*/
const whichPython3 = _.partial(cachedWhich, `${NAME_PYTHON}3`, {nothrow: true});

/**
* Check if `mkdocs` is installed
*/
export const isMkDocsInstalled = _.memoize(async (): Promise<boolean> => {
// see if it's in PATH
const mkDocsPath = await cachedWhich(NAME_MKDOCS, {nothrow: true});
if (mkDocsPath) {
return true;
}
// if it isn't, it should be invokable via `python -m`
const pythonPath = await findPython();
if (!pythonPath) {
return false;
}
try {
await exec(pythonPath, ['-m', NAME_MKDOCS]);
return true;
} catch {
return false;
}
});

/**
* `mike` cannot be invoked via `python -m`, so we need to find the script.
*/
Expand Down Expand Up @@ -225,6 +251,17 @@ export const findPython = _.memoize(
async (): Promise<string | null> => (await whichPython3()) ?? (await whichPython()),
);

/**
* Check if a path to Python exists, otherwise raise DocutilsError
*/
export async function requirePython(pythonPath?: string): Promise<string> {
const foundPythonPath = pythonPath ?? (await findPython());
if (!foundPythonPath) {
throw new DocutilsError(MESSAGE_PYTHON_MISSING);
}
return foundPythonPath;
}

/**
* Reads an `mkdocs.yml` file, merges inherited configs, and returns the result. The result is cached.
*
Expand Down
14 changes: 7 additions & 7 deletions packages/docutils/lib/init.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
*/

import * as JSON5 from 'json5';
import {NAME_MKDOCS_YML, NAME_TSCONFIG_JSON, NAME_PYTHON, PIP_ENV_VARS, REQUIREMENTS_TXT_PATH} from './constants';
import {NAME_MKDOCS_YML, NAME_TSCONFIG_JSON, PIP_ENV_VARS, REQUIREMENTS_TXT_PATH} from './constants';
import YAML from 'yaml';
import {exec} from 'teen_process';
import {Simplify} from 'type-fest';
Expand All @@ -15,7 +15,7 @@ import type { ScaffoldTask } from './scaffold';
import {getLogger} from './logger';
import {MkDocsYml, TsConfigJson} from './model';
import _ from 'lodash';
import {findPython, stringifyJson5, stringifyYaml} from './fs';
import {requirePython, stringifyJson5, stringifyYaml} from './fs';

/**
* Data for the base `mkdocs.yml` file
Expand Down Expand Up @@ -139,7 +139,7 @@ export async function initPython({
dryRun = false,
upgrade = false,
}: InitPythonOptions = {}): Promise<void> {
pythonPath = pythonPath ?? (await findPython()) ?? NAME_PYTHON;
const foundPythonPath = await requirePython(pythonPath);

const args = ['-m', 'pip', 'install', '-r', REQUIREMENTS_TXT_PATH];
if (upgrade) {
Expand All @@ -148,19 +148,19 @@ export async function initPython({
if (dryRun) {
dryRunLog.info(
'Would execute command: %s %s (environment variables: %s)',
pythonPath,
foundPythonPath,
args.join(' '),
PIP_ENV_VARS,
);
} else {
log.debug('Executing command: %s %s (environment variables: %s)',
pythonPath,
foundPythonPath,
args.join(' '),
PIP_ENV_VARS,
);
log.info('Installing Python dependencies...');
try {
const result = await exec(pythonPath, args, {env: PIP_ENV_VARS, shell: true});
const result = await exec(foundPythonPath, args, {env: PIP_ENV_VARS, shell: true});
const {code, stdout} = result;
if (code !== 0) {
throw new DocutilsError(`Could not install Python dependencies. Reason: ${stdout}`);
Expand All @@ -171,7 +171,7 @@ export async function initPython({
);
}
}
log.success('Installed Python dependencies (or dependencies already installed)');
log.success('Successfully installed Python dependencies');
}

/**
Expand Down
39 changes: 19 additions & 20 deletions packages/docutils/lib/scaffold.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,8 @@ import {JsonValue, JsonObject} from 'type-fest';
import {DocutilsError} from './error';
import {relative} from './util';
import _ from 'lodash';
import {stringifyJson, readPackageJson, safeWriteFile} from './fs';
import {NAME_ERR_ENOENT, NAME_ERR_EEXIST} from './constants';
import {stringifyJson, readPackageJson, writeFileString} from './fs';
import {NAME_ERR_ENOENT} from './constants';

const log = getLogger('init');
const dryRunLog = getLogger('dry-run', log);
Expand Down Expand Up @@ -91,7 +91,7 @@ export function createScaffoldTask<Opts extends ScaffoldTaskOptions, T extends J
dest = dest ?? path.join(pkgDir, defaultFilename);
const relativeDest = relativePath(dest);
log.debug('Initializing %s', relativeDest);
let shouldWriteDest = false;
let destChangesNeeded = false;
let isNew = false;
let destContent: T;
let result: ScaffoldTaskResult<T>;
Expand All @@ -103,7 +103,7 @@ export function createScaffoldTask<Opts extends ScaffoldTaskOptions, T extends J
if (err.code !== NAME_ERR_ENOENT) {
throw err;
}
shouldWriteDest = true;
destChangesNeeded = true;
log.debug('Creating new file %s', relativeDest);
destContent = {} as T;
isNew = true;
Expand All @@ -112,9 +112,9 @@ export function createScaffoldTask<Opts extends ScaffoldTaskOptions, T extends J
const defaults: T = transform(defaultContent, opts, pkg);
const finalDestContent: T = _.defaultsDeep({}, destContent, defaults);

shouldWriteDest = shouldWriteDest || !_.isEqual(destContent, finalDestContent);
destChangesNeeded = destChangesNeeded || !_.isEqual(destContent, finalDestContent);

if (shouldWriteDest) {
if (destChangesNeeded) {
log.info('Changes needed in %s', relativeDest);
log.debug('Original %s: %O', relativeDest, destContent);
log.debug('Final %s: %O', relativeDest, finalDestContent);
Expand All @@ -126,20 +126,19 @@ export function createScaffoldTask<Opts extends ScaffoldTaskOptions, T extends J
return result;
}

try {
await safeWriteFile(dest, finalDestContent, overwrite);
if (isNew) {
log.success('Initialized %s', description);
} else {
log.success('Updated %s', description);
}
} catch (e) {
const err = e as NodeJS.ErrnoException;
// this should only be thrown if `force` is false
if (err.code === NAME_ERR_EEXIST) {
log.info(`${relativeDest} already exists; continuing...`);
log.debug(`Tried to apply patch:\n\n${patch}`);
} else {
if (!isNew && !overwrite) {
log.info('File %s already exists, continuing (enable overwrite with "--force")', relativeDest);
log.debug('Tried to apply patch:\n\n%s', patch);
} else {
try {
await writeFileString(dest, finalDestContent);
if (isNew) {
log.success('Initialized %s', description);
} else {
log.success('Updated %s', description);
}
} catch (e) {
const err = e as NodeJS.ErrnoException;
throw new DocutilsError(`Could not write to ${relativeDest}. Reason: ${err.message}`, {
cause: err,
});
Expand Down
Loading
0