Added support for updating tsconfig.json when using astro add (#4959)
* Added support for updating tsconfig.json when using astro add * Refactor * Remove unneeded change * Fix build failling due to type difference * Extend changeset description
This commit is contained in:
parent
a5e3ecc803
commit
0ea6187f95
15 changed files with 388 additions and 36 deletions
18
.changeset/giant-news-speak.md
Normal file
18
.changeset/giant-news-speak.md
Normal file
|
@ -0,0 +1,18 @@
|
|||
---
|
||||
'astro': minor
|
||||
---
|
||||
|
||||
Added support for updating TypeScript settings automatically when using `astro add`
|
||||
|
||||
The `astro add` command will now automatically update your `tsconfig.json` with the proper TypeScript settings needed for the chosen frameworks.
|
||||
|
||||
For instance, typing `astro add solid` will update your `tsconfig.json` with the following settings, per [Solid's TypeScript guide](https://www.solidjs.com/guides/typescript):
|
||||
|
||||
```json
|
||||
{
|
||||
"compilerOptions": {
|
||||
"jsx": "preserve",
|
||||
"jsxImportSource": "solid-js"
|
||||
}
|
||||
}
|
||||
```
|
|
@ -53,6 +53,9 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"overrides": {
|
||||
"tsconfig-resolver>type-fest": "3.0.0"
|
||||
},
|
||||
"peerDependencyRules": {
|
||||
"ignoreMissing": [
|
||||
"rollup",
|
||||
|
|
|
@ -116,6 +116,7 @@
|
|||
"common-ancestor-path": "^1.0.1",
|
||||
"cookie": "^0.5.0",
|
||||
"debug": "^4.3.4",
|
||||
"deepmerge-ts": "^4.2.2",
|
||||
"diff": "^5.1.0",
|
||||
"eol": "^0.9.1",
|
||||
"es-module-lexer": "^0.10.5",
|
||||
|
|
|
@ -3,14 +3,20 @@ import boxen from 'boxen';
|
|||
import { diffWords } from 'diff';
|
||||
import { execa } from 'execa';
|
||||
import { existsSync, promises as fs } from 'fs';
|
||||
import { bold, cyan, dim, green, magenta, yellow } from 'kleur/colors';
|
||||
import { bold, cyan, dim, green, magenta, red, yellow } from 'kleur/colors';
|
||||
import ora from 'ora';
|
||||
import path from 'path';
|
||||
import preferredPM from 'preferred-pm';
|
||||
import prompts from 'prompts';
|
||||
import { fileURLToPath, pathToFileURL } from 'url';
|
||||
import type yargs from 'yargs-parser';
|
||||
import { resolveConfigPath } from '../config/index.js';
|
||||
import { loadTSConfig, resolveConfigPath } from '../config/index.js';
|
||||
import {
|
||||
defaultTSConfig,
|
||||
frameworkWithTSSettings,
|
||||
presets,
|
||||
updateTSConfigForFramework,
|
||||
} from '../config/tsconfig.js';
|
||||
import { debug, info, LogOptions } from '../logger/core.js';
|
||||
import * as msg from '../messages.js';
|
||||
import { printHelp } from '../messages.js';
|
||||
|
@ -239,7 +245,7 @@ export default async function add(names: string[], { cwd, flags, logging, teleme
|
|||
switch (configResult) {
|
||||
case UpdateResult.cancelled: {
|
||||
info(logging, null, msg.cancelled(`Your configuration has ${bold('NOT')} been updated.`));
|
||||
return;
|
||||
break;
|
||||
}
|
||||
case UpdateResult.none: {
|
||||
const pkgURL = new URL('./package.json', configURL);
|
||||
|
@ -253,12 +259,12 @@ export default async function add(names: string[], { cwd, flags, logging, teleme
|
|||
);
|
||||
if (missingDeps.length === 0) {
|
||||
info(logging, null, msg.success(`Configuration up-to-date.`));
|
||||
return;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
info(logging, null, msg.success(`Configuration up-to-date.`));
|
||||
return;
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
const list = integrations.map((integration) => ` - ${integration.packageName}`).join('\n');
|
||||
|
@ -273,6 +279,29 @@ export default async function add(names: string[], { cwd, flags, logging, teleme
|
|||
);
|
||||
}
|
||||
}
|
||||
|
||||
const updateTSConfigResult = await updateTSConfig(cwd, logging, integrations, flags);
|
||||
|
||||
switch (updateTSConfigResult) {
|
||||
case UpdateResult.none: {
|
||||
break;
|
||||
}
|
||||
case UpdateResult.cancelled: {
|
||||
info(
|
||||
logging,
|
||||
null,
|
||||
msg.cancelled(`Your TypeScript configuration has ${bold('NOT')} been updated.`)
|
||||
);
|
||||
break;
|
||||
}
|
||||
case UpdateResult.failure: {
|
||||
throw new Error(
|
||||
`Unknown error parsing tsconfig.json or jsconfig.json. Could not update TypeScript settings.`
|
||||
);
|
||||
}
|
||||
default:
|
||||
info(logging, null, msg.success(`Successfully updated TypeScript settings`));
|
||||
}
|
||||
}
|
||||
|
||||
function isAdapter(
|
||||
|
@ -471,29 +500,13 @@ async function updateAstroConfig({
|
|||
return UpdateResult.none;
|
||||
}
|
||||
|
||||
let changes = [];
|
||||
for (const change of diffWords(input, output)) {
|
||||
let lines = change.value.trim().split('\n').slice(0, change.count);
|
||||
if (lines.length === 0) continue;
|
||||
if (change.added) {
|
||||
if (!change.value.trim()) continue;
|
||||
changes.push(change.value);
|
||||
}
|
||||
}
|
||||
if (changes.length === 0) {
|
||||
const diff = getDiffContent(input, output);
|
||||
|
||||
if (!diff) {
|
||||
return UpdateResult.none;
|
||||
}
|
||||
|
||||
let diffed = output;
|
||||
for (let newContent of changes) {
|
||||
const coloredOutput = newContent
|
||||
.split('\n')
|
||||
.map((ln) => (ln ? green(ln) : ''))
|
||||
.join('\n');
|
||||
diffed = diffed.replace(newContent, coloredOutput);
|
||||
}
|
||||
|
||||
const message = `\n${boxen(diffed, {
|
||||
const message = `\n${boxen(diff, {
|
||||
margin: 0.5,
|
||||
padding: 0.5,
|
||||
borderStyle: 'round',
|
||||
|
@ -533,6 +546,7 @@ interface InstallCommand {
|
|||
flags: string[];
|
||||
dependencies: string[];
|
||||
}
|
||||
|
||||
async function getInstallIntegrationsCommand({
|
||||
integrations,
|
||||
cwd = process.cwd(),
|
||||
|
@ -727,6 +741,113 @@ export async function validateIntegrations(integrations: string[]): Promise<Inte
|
|||
}
|
||||
}
|
||||
|
||||
async function updateTSConfig(
|
||||
cwd = process.cwd(),
|
||||
logging: LogOptions,
|
||||
integrationsInfo: IntegrationInfo[],
|
||||
flags: yargs.Arguments
|
||||
): Promise<UpdateResult> {
|
||||
const integrations = integrationsInfo.map(
|
||||
(integration) => integration.id as frameworkWithTSSettings
|
||||
);
|
||||
const firstIntegrationWithTSSettings = integrations.find((integration) =>
|
||||
presets.has(integration)
|
||||
);
|
||||
|
||||
if (!firstIntegrationWithTSSettings) {
|
||||
return UpdateResult.none;
|
||||
}
|
||||
|
||||
const inputConfig = loadTSConfig(cwd, false);
|
||||
const configFileName = inputConfig.exists ? inputConfig.path.split('/').pop() : 'tsconfig.json';
|
||||
|
||||
if (inputConfig.reason === 'invalid-config') {
|
||||
return UpdateResult.failure;
|
||||
}
|
||||
|
||||
if (inputConfig.reason === 'not-found') {
|
||||
debug('add', "Couldn't find tsconfig.json or jsconfig.json, generating one");
|
||||
}
|
||||
|
||||
const outputConfig = updateTSConfigForFramework(
|
||||
inputConfig.exists ? inputConfig.config : defaultTSConfig,
|
||||
firstIntegrationWithTSSettings
|
||||
);
|
||||
|
||||
const input = inputConfig.exists ? JSON.stringify(inputConfig.config, null, 2) : '';
|
||||
const output = JSON.stringify(outputConfig, null, 2);
|
||||
const diff = getDiffContent(input, output);
|
||||
|
||||
if (!diff) {
|
||||
return UpdateResult.none;
|
||||
}
|
||||
|
||||
const message = `\n${boxen(diff, {
|
||||
margin: 0.5,
|
||||
padding: 0.5,
|
||||
borderStyle: 'round',
|
||||
title: configFileName,
|
||||
})}\n`;
|
||||
|
||||
info(
|
||||
logging,
|
||||
null,
|
||||
`\n ${magenta(`Astro will make the following changes to your ${configFileName}:`)}\n${message}`
|
||||
);
|
||||
|
||||
// Every major framework, apart from Vue and Svelte requires different `jsxImportSource`, as such it's impossible to config
|
||||
// all of them in the same `tsconfig.json`. However, Vue only need `"jsx": "preserve"` for template intellisense which
|
||||
// can be compatible with some frameworks (ex: Solid), though ultimately run into issues on the current version of Volar
|
||||
const conflictingIntegrations = [...Object.keys(presets).filter((config) => config !== 'vue')];
|
||||
const hasConflictingIntegrations =
|
||||
integrations.filter((integration) => presets.has(integration)).length > 1 &&
|
||||
integrations.filter((integration) => conflictingIntegrations.includes(integration)).length > 0;
|
||||
|
||||
if (hasConflictingIntegrations) {
|
||||
info(
|
||||
logging,
|
||||
null,
|
||||
red(
|
||||
` ${bold(
|
||||
'Caution:'
|
||||
)} Selected UI frameworks require conflicting tsconfig.json settings, as such only settings for ${bold(
|
||||
firstIntegrationWithTSSettings
|
||||
)} were used.\n More information: https://docs.astro.build/en/guides/typescript/#errors-typing-multiple-jsx-frameworks-at-the-same-time\n`
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
// TODO: Remove this when Volar 1.0 ships, as it fixes the issue.
|
||||
// Info: https://github.com/johnsoncodehk/volar/discussions/592#discussioncomment-3660903
|
||||
if (
|
||||
integrations.includes('vue') &&
|
||||
hasConflictingIntegrations &&
|
||||
((outputConfig.compilerOptions?.jsx !== 'preserve' &&
|
||||
outputConfig.compilerOptions?.jsxImportSource !== undefined) ||
|
||||
integrations.includes('react')) // https://docs.astro.build/en/guides/typescript/#vue-components-are-mistakenly-typed-by-the-typesreact-package-when-installed
|
||||
) {
|
||||
info(
|
||||
logging,
|
||||
null,
|
||||
red(
|
||||
` ${bold(
|
||||
'Caution:'
|
||||
)} Using Vue together with a JSX framework can lead to type checking issues inside Vue files.\n More information: https://docs.astro.build/en/guides/typescript/#vue-components-are-mistakenly-typed-by-the-typesreact-package-when-installed\n`
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
if (await askToContinue({ flags })) {
|
||||
await fs.writeFile(inputConfig?.path ?? path.join(cwd, 'tsconfig.json'), output, {
|
||||
encoding: 'utf-8',
|
||||
});
|
||||
debug('add', `Updated ${configFileName} file`);
|
||||
return UpdateResult.updated;
|
||||
} else {
|
||||
return UpdateResult.cancelled;
|
||||
}
|
||||
}
|
||||
|
||||
function parseIntegrationName(spec: string) {
|
||||
const result = parseNpmName(spec);
|
||||
if (!result) return;
|
||||
|
@ -755,3 +876,29 @@ async function askToContinue({ flags }: { flags: yargs.Arguments }): Promise<boo
|
|||
|
||||
return Boolean(response.askToContinue);
|
||||
}
|
||||
|
||||
function getDiffContent(input: string, output: string): string | null {
|
||||
let changes = [];
|
||||
for (const change of diffWords(input, output)) {
|
||||
let lines = change.value.trim().split('\n').slice(0, change.count);
|
||||
if (lines.length === 0) continue;
|
||||
if (change.added) {
|
||||
if (!change.value.trim()) continue;
|
||||
changes.push(change.value);
|
||||
}
|
||||
}
|
||||
if (changes.length === 0) {
|
||||
return null;
|
||||
}
|
||||
|
||||
let diffed = output;
|
||||
for (let newContent of changes) {
|
||||
const coloredOutput = newContent
|
||||
.split('\n')
|
||||
.map((ln) => (ln ? green(ln) : ''))
|
||||
.join('\n');
|
||||
diffed = diffed.replace(newContent, coloredOutput);
|
||||
}
|
||||
|
||||
return diffed;
|
||||
}
|
||||
|
|
|
@ -7,4 +7,4 @@ export {
|
|||
} from './config.js';
|
||||
export type { AstroConfigSchema } from './schema';
|
||||
export { createSettings } from './settings.js';
|
||||
export { loadTSConfig } from './tsconfig.js';
|
||||
export { loadTSConfig, updateTSConfigForFramework } from './tsconfig.js';
|
||||
|
|
|
@ -1,11 +1,100 @@
|
|||
import { deepmerge } from 'deepmerge-ts';
|
||||
import * as tsr from 'tsconfig-resolver';
|
||||
import { existsSync } from 'fs';
|
||||
import { join } from 'path';
|
||||
|
||||
export function loadTSConfig(cwd: string | undefined): tsr.TsConfigResult | undefined {
|
||||
for (const searchName of ['tsconfig.json', 'jsconfig.json']) {
|
||||
const config = tsr.tsconfigResolverSync({ cwd, searchName });
|
||||
if (config.exists) {
|
||||
return config;
|
||||
export const defaultTSConfig: tsr.TsConfigJson = { extends: 'astro/tsconfigs/base' };
|
||||
|
||||
export type frameworkWithTSSettings = 'vue' | 'react' | 'preact' | 'solid-js';
|
||||
// The following presets unfortunately cannot be inside the specific integrations, as we need
|
||||
// them even in cases where the integrations are not installed
|
||||
export const presets = new Map<frameworkWithTSSettings, tsr.TsConfigJson>([
|
||||
[
|
||||
'vue', // Settings needed for template intellisense when using Volar
|
||||
{
|
||||
compilerOptions: {
|
||||
jsx: 'preserve',
|
||||
},
|
||||
},
|
||||
],
|
||||
[
|
||||
'react', // Default TypeScript settings, but we need to redefine them in case the users changed them previously
|
||||
{
|
||||
compilerOptions: {
|
||||
jsx: 'react-jsx',
|
||||
jsxImportSource: 'react',
|
||||
},
|
||||
},
|
||||
],
|
||||
[
|
||||
'preact', // https://preactjs.com/guide/v10/typescript/#typescript-configuration
|
||||
{
|
||||
compilerOptions: {
|
||||
jsx: 'react-jsx',
|
||||
jsxImportSource: 'preact',
|
||||
},
|
||||
},
|
||||
],
|
||||
[
|
||||
'solid-js', // https://www.solidjs.com/guides/typescript#configuring-typescript
|
||||
{
|
||||
compilerOptions: {
|
||||
jsx: 'preserve',
|
||||
jsxImportSource: 'solid-js',
|
||||
},
|
||||
},
|
||||
],
|
||||
]);
|
||||
|
||||
/**
|
||||
* Load a tsconfig.json or jsconfig.json is the former is not found
|
||||
* @param cwd Directory to start from
|
||||
* @param resolve Determine if the function should go up directories like TypeScript would
|
||||
*/
|
||||
export function loadTSConfig(cwd: string | undefined, resolve = true): tsr.TsConfigResult {
|
||||
cwd = cwd ?? process.cwd();
|
||||
let config = tsr.tsconfigResolverSync({
|
||||
cwd,
|
||||
filePath: resolve ? undefined : cwd,
|
||||
});
|
||||
|
||||
// When a direct filepath is provided to `tsconfigResolver`, it'll instead return invalid-config even when
|
||||
// the file does not exists. We'll manually handle this so we can provide better errors to users
|
||||
if (!resolve && config.reason === 'invalid-config' && !existsSync(join(cwd, 'tsconfig.json'))) {
|
||||
config = { reason: 'not-found', path: undefined, exists: false };
|
||||
} else {
|
||||
return config;
|
||||
}
|
||||
|
||||
// If we couldn't find a tsconfig.json, try to load a jsconfig.json instead
|
||||
if (config.reason === 'not-found') {
|
||||
const jsconfig = tsr.tsconfigResolverSync({
|
||||
cwd,
|
||||
filePath: resolve ? undefined : cwd,
|
||||
searchName: 'jsconfig.json',
|
||||
});
|
||||
|
||||
if (
|
||||
!resolve &&
|
||||
jsconfig.reason === 'invalid-config' &&
|
||||
!existsSync(join(cwd, 'jsconfig.json'))
|
||||
) {
|
||||
return { reason: 'not-found', path: undefined, exists: false };
|
||||
} else {
|
||||
return jsconfig;
|
||||
}
|
||||
}
|
||||
return undefined;
|
||||
|
||||
return config;
|
||||
}
|
||||
|
||||
export function updateTSConfigForFramework(
|
||||
target: tsr.TsConfigJson,
|
||||
framework: frameworkWithTSSettings
|
||||
): tsr.TsConfigJson {
|
||||
if (!presets.has(framework)) {
|
||||
return target;
|
||||
}
|
||||
|
||||
return deepmerge(target, presets.get(framework)!);
|
||||
}
|
||||
|
|
|
@ -226,8 +226,8 @@ export function resolveJsToTs(filePath: string) {
|
|||
}
|
||||
|
||||
export const AggregateError =
|
||||
typeof globalThis.AggregateError !== 'undefined'
|
||||
? globalThis.AggregateError
|
||||
typeof (globalThis as any).AggregateError !== 'undefined'
|
||||
? (globalThis as any).AggregateError
|
||||
: class extends Error {
|
||||
errors: Array<any> = [];
|
||||
constructor(errors: Iterable<any>, message?: string | undefined) {
|
||||
|
|
3
packages/astro/test/fixtures/tsconfig-handling/invalid/tsconfig.json
vendored
Normal file
3
packages/astro/test/fixtures/tsconfig-handling/invalid/tsconfig.json
vendored
Normal file
|
@ -0,0 +1,3 @@
|
|||
{
|
||||
"buildOptions":
|
||||
}
|
3
packages/astro/test/fixtures/tsconfig-handling/jsconfig/jsconfig.json
vendored
Normal file
3
packages/astro/test/fixtures/tsconfig-handling/jsconfig/jsconfig.json
vendored
Normal file
|
@ -0,0 +1,3 @@
|
|||
{
|
||||
"files": ["im-a-test-js"]
|
||||
}
|
0
packages/astro/test/fixtures/tsconfig-handling/missing/.gitkeep
vendored
Normal file
0
packages/astro/test/fixtures/tsconfig-handling/missing/.gitkeep
vendored
Normal file
0
packages/astro/test/fixtures/tsconfig-handling/nested-folder/.gitkeep
vendored
Normal file
0
packages/astro/test/fixtures/tsconfig-handling/nested-folder/.gitkeep
vendored
Normal file
3
packages/astro/test/fixtures/tsconfig-handling/tsconfig.json
vendored
Normal file
3
packages/astro/test/fixtures/tsconfig-handling/tsconfig.json
vendored
Normal file
|
@ -0,0 +1,3 @@
|
|||
{
|
||||
"files": ["im-a-test"]
|
||||
}
|
68
packages/astro/test/units/config/config-tsconfig.test.js
Normal file
68
packages/astro/test/units/config/config-tsconfig.test.js
Normal file
|
@ -0,0 +1,68 @@
|
|||
import { expect } from 'chai';
|
||||
import { fileURLToPath } from 'url';
|
||||
import { loadTSConfig, updateTSConfigForFramework } from '../../../dist/core/config/index.js';
|
||||
import * as path from 'path';
|
||||
import * as tsr from 'tsconfig-resolver';
|
||||
|
||||
const cwd = fileURLToPath(new URL('../../fixtures/tsconfig-handling/', import.meta.url));
|
||||
|
||||
describe('TSConfig handling', () => {
|
||||
beforeEach(() => {
|
||||
// `tsconfig-resolver` has a weird internal cache that only vaguely respect its own rules when not resolving
|
||||
// so we need to clear it before each test or we'll get false positives. This should only be relevant in tests.
|
||||
tsr.clearCache();
|
||||
});
|
||||
|
||||
describe('tsconfig / jsconfig loading', () => {
|
||||
it('can load tsconfig.json', () => {
|
||||
const config = loadTSConfig(cwd);
|
||||
|
||||
expect(config.exists).to.equal(true);
|
||||
expect(config.config.files).to.deep.equal(['im-a-test']);
|
||||
});
|
||||
|
||||
it('can resolve tsconfig.json up directories', () => {
|
||||
const config = loadTSConfig(path.join(cwd, 'nested-folder'));
|
||||
|
||||
expect(config.exists).to.equal(true);
|
||||
expect(config.path).to.equal(path.join(cwd, 'tsconfig.json'));
|
||||
expect(config.config.files).to.deep.equal(['im-a-test']);
|
||||
});
|
||||
|
||||
it('can fallback to jsconfig.json if tsconfig.json does not exists', () => {
|
||||
const config = loadTSConfig(path.join(cwd, 'jsconfig'), false);
|
||||
|
||||
expect(config.exists).to.equal(true);
|
||||
expect(config.path).to.equal(path.join(cwd, 'jsconfig', 'jsconfig.json'));
|
||||
expect(config.config.files).to.deep.equal(['im-a-test-js']);
|
||||
});
|
||||
|
||||
it('properly return errors when not resolving', () => {
|
||||
const invalidConfig = loadTSConfig(path.join(cwd, 'invalid'), false);
|
||||
const missingConfig = loadTSConfig(path.join(cwd, 'missing'), false);
|
||||
|
||||
expect(invalidConfig.exists).to.equal(false);
|
||||
expect(invalidConfig.reason).to.equal('invalid-config');
|
||||
|
||||
expect(missingConfig.exists).to.equal(false);
|
||||
expect(missingConfig.reason).to.equal('not-found');
|
||||
});
|
||||
});
|
||||
|
||||
describe('tsconfig / jsconfig updates', () => {
|
||||
it('can update a tsconfig with a framework config', () => {
|
||||
const config = loadTSConfig(cwd);
|
||||
const updatedConfig = updateTSConfigForFramework(config.config, 'react');
|
||||
|
||||
expect(config.config).to.not.equal('react-jsx');
|
||||
expect(updatedConfig.compilerOptions.jsx).to.equal('react-jsx');
|
||||
});
|
||||
|
||||
it('produce no changes on invalid frameworks', () => {
|
||||
const config = loadTSConfig(cwd);
|
||||
const updatedConfig = updateTSConfigForFramework(config.config, 'doesnt-exist');
|
||||
|
||||
expect(config.config).to.deep.equal(updatedConfig);
|
||||
});
|
||||
});
|
||||
});
|
|
@ -47,7 +47,8 @@
|
|||
},
|
||||
"peerDependencies": {
|
||||
"react": "^17.0.2 || ^18.0.0",
|
||||
"react-dom": "^17.0.2 || ^18.0.0"
|
||||
"react-dom": "^17.0.2 || ^18.0.0",
|
||||
"@types/react": "^17.0.50 || ^18.0.21"
|
||||
},
|
||||
"engines": {
|
||||
"node": "^14.18.0 || >=16.12.0"
|
||||
|
|
|
@ -1,5 +1,8 @@
|
|||
lockfileVersion: 5.4
|
||||
|
||||
overrides:
|
||||
tsconfig-resolver>type-fest: 3.0.0
|
||||
|
||||
packageExtensionsChecksum: 01871422d489547c532184effb134b35
|
||||
|
||||
patchedDependencies:
|
||||
|
@ -405,6 +408,7 @@ importers:
|
|||
common-ancestor-path: ^1.0.1
|
||||
cookie: ^0.5.0
|
||||
debug: ^4.3.4
|
||||
deepmerge-ts: ^4.2.2
|
||||
diff: ^5.1.0
|
||||
eol: ^0.9.1
|
||||
es-module-lexer: ^0.10.5
|
||||
|
@ -475,6 +479,7 @@ importers:
|
|||
common-ancestor-path: 1.0.1
|
||||
cookie: 0.5.0
|
||||
debug: 4.3.4
|
||||
deepmerge-ts: 4.2.2
|
||||
diff: 5.1.0
|
||||
eol: 0.9.1
|
||||
es-module-lexer: 0.10.5
|
||||
|
@ -11257,6 +11262,11 @@ packages:
|
|||
resolution: {integrity: sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==}
|
||||
dev: true
|
||||
|
||||
/deepmerge-ts/4.2.2:
|
||||
resolution: {integrity: sha512-Ka3Kb21tiWjvQvS9U+1Dx+aqFAHsdTnMdYptLTmC2VAmDFMugWMY1e15aTODstipmCun8iNuqeSfcx6rsUUk0Q==}
|
||||
engines: {node: '>=12.4.0'}
|
||||
dev: false
|
||||
|
||||
/deepmerge/4.2.2:
|
||||
resolution: {integrity: sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==}
|
||||
engines: {node: '>=0.10.0'}
|
||||
|
@ -17177,7 +17187,8 @@ packages:
|
|||
json5: 2.2.1
|
||||
resolve: 1.22.1
|
||||
strip-bom: 4.0.0
|
||||
type-fest: 0.13.1
|
||||
type-fest: 3.0.0
|
||||
dev: false
|
||||
|
||||
/tsconfig/7.0.0:
|
||||
resolution: {integrity: sha512-vZXmzPrL+EmC4T/4rVlT2jNVMWCi/O4DIiSj3UHg1OE5kCKbk4mfrXc6dZksLgRM/TZlKnousKH9bbTazUWRRw==}
|
||||
|
@ -17402,6 +17413,11 @@ packages:
|
|||
engines: {node: '>=12.20'}
|
||||
dev: false
|
||||
|
||||
/type-fest/3.0.0:
|
||||
resolution: {integrity: sha512-MINvUN5ug9u+0hJDzSZNSnuKXI8M4F5Yvb6SQZ2CYqe7SgKXKOosEcU5R7tRgo85I6eAVBbkVF7TCvB4AUK2xQ==}
|
||||
engines: {node: '>=14.16'}
|
||||
dev: false
|
||||
|
||||
/type-is/1.6.18:
|
||||
resolution: {integrity: sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==}
|
||||
engines: {node: '>= 0.6'}
|
||||
|
|
Loading…
Reference in a new issue