mirror of
https://github.com/whyour/qinglong.git
synced 2025-05-22 22:36:06 +08:00
写入文件增加文件锁,避免竞争条件引起文件内容异常
This commit is contained in:
parent
7d43b14f81
commit
05f8bbd26e
|
@ -7,6 +7,7 @@ import { celebrate, Joi } from 'celebrate';
|
||||||
import { join } from 'path';
|
import { join } from 'path';
|
||||||
import { SAMPLE_FILES } from '../config/const';
|
import { SAMPLE_FILES } from '../config/const';
|
||||||
import ConfigService from '../services/config';
|
import ConfigService from '../services/config';
|
||||||
|
import { writeFileWithLock } from '../shared/utils';
|
||||||
const route = Router();
|
const route = Router();
|
||||||
|
|
||||||
export default (app: Router) => {
|
export default (app: Router) => {
|
||||||
|
@ -77,7 +78,7 @@ export default (app: Router) => {
|
||||||
if (name.startsWith('data/scripts/')) {
|
if (name.startsWith('data/scripts/')) {
|
||||||
path = join(config.rootPath, name);
|
path = join(config.rootPath, name);
|
||||||
}
|
}
|
||||||
await fs.writeFile(path, content);
|
await writeFileWithLock(path, content);
|
||||||
res.send({ code: 200, message: '保存成功' });
|
res.send({ code: 200, message: '保存成功' });
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
return next(e);
|
return next(e);
|
||||||
|
|
|
@ -8,6 +8,7 @@ import { celebrate, Joi } from 'celebrate';
|
||||||
import path, { join, parse } from 'path';
|
import path, { join, parse } from 'path';
|
||||||
import ScriptService from '../services/script';
|
import ScriptService from '../services/script';
|
||||||
import multer from 'multer';
|
import multer from 'multer';
|
||||||
|
import { writeFileWithLock } from '../shared/utils';
|
||||||
const route = Router();
|
const route = Router();
|
||||||
|
|
||||||
const storage = multer.diskStorage({
|
const storage = multer.diskStorage({
|
||||||
|
@ -156,7 +157,7 @@ export default (app: Router) => {
|
||||||
await rmPath(originFilePath);
|
await rmPath(originFilePath);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
await fs.writeFile(filePath, content);
|
await writeFileWithLock(filePath, content);
|
||||||
return res.send({ code: 200 });
|
return res.send({ code: 200 });
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
return next(e);
|
return next(e);
|
||||||
|
@ -182,7 +183,7 @@ export default (app: Router) => {
|
||||||
path: string;
|
path: string;
|
||||||
};
|
};
|
||||||
const filePath = join(config.scriptPath, path, filename);
|
const filePath = join(config.scriptPath, path, filename);
|
||||||
await fs.writeFile(filePath, content);
|
await writeFileWithLock(filePath, content);
|
||||||
return res.send({ code: 200 });
|
return res.send({ code: 200 });
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
return next(e);
|
return next(e);
|
||||||
|
@ -261,7 +262,7 @@ export default (app: Router) => {
|
||||||
let { filename, content, path } = req.body;
|
let { filename, content, path } = req.body;
|
||||||
const { name, ext } = parse(filename);
|
const { name, ext } = parse(filename);
|
||||||
const filePath = join(config.scriptPath, path, `${name}.swap${ext}`);
|
const filePath = join(config.scriptPath, path, `${name}.swap${ext}`);
|
||||||
await fs.writeFile(filePath, content || '', { encoding: 'utf8' });
|
await writeFileWithLock(filePath, content || '');
|
||||||
|
|
||||||
const scriptService = Container.get(ScriptService);
|
const scriptService = Container.get(ScriptService);
|
||||||
const result = await scriptService.runScript(filePath);
|
const result = await scriptService.runScript(filePath);
|
||||||
|
|
|
@ -10,6 +10,7 @@ import { load } from 'js-yaml';
|
||||||
import config from './index';
|
import config from './index';
|
||||||
import { TASK_COMMAND } from './const';
|
import { TASK_COMMAND } from './const';
|
||||||
import Logger from '../loaders/logger';
|
import Logger from '../loaders/logger';
|
||||||
|
import { writeFileWithLock } from '../shared/utils';
|
||||||
|
|
||||||
export * from './share';
|
export * from './share';
|
||||||
|
|
||||||
|
@ -170,7 +171,7 @@ export async function fileExist(file: any) {
|
||||||
|
|
||||||
export async function createFile(file: string, data: string = '') {
|
export async function createFile(file: string, data: string = '') {
|
||||||
await fs.mkdir(path.dirname(file), { recursive: true });
|
await fs.mkdir(path.dirname(file), { recursive: true });
|
||||||
await fs.writeFile(file, data);
|
await writeFileWithLock(file, data);
|
||||||
}
|
}
|
||||||
|
|
||||||
export async function handleLogPath(
|
export async function handleLogPath(
|
||||||
|
|
|
@ -3,6 +3,7 @@ import path from 'path';
|
||||||
import os from 'os';
|
import os from 'os';
|
||||||
import Logger from './logger';
|
import Logger from './logger';
|
||||||
import { fileExist } from '../config/util';
|
import { fileExist } from '../config/util';
|
||||||
|
import { writeFileWithLock } from '../shared/utils';
|
||||||
|
|
||||||
const rootPath = process.env.QL_DIR as string;
|
const rootPath = process.env.QL_DIR as string;
|
||||||
let dataPath = path.join(rootPath, 'data/');
|
let dataPath = path.join(rootPath, 'data/');
|
||||||
|
@ -99,46 +100,46 @@ export default async () => {
|
||||||
// 初始化文件
|
// 初始化文件
|
||||||
|
|
||||||
if (!confFileExist) {
|
if (!confFileExist) {
|
||||||
await fs.writeFile(confFile, await fs.readFile(sampleConfigFile));
|
await writeFileWithLock(confFile, await fs.readFile(sampleConfigFile));
|
||||||
}
|
}
|
||||||
|
|
||||||
await fs.writeFile(jsNotifyFile, await fs.readFile(sampleNotifyJsFile));
|
await writeFileWithLock(jsNotifyFile, await fs.readFile(sampleNotifyJsFile));
|
||||||
await fs.writeFile(pyNotifyFile, await fs.readFile(sampleNotifyPyFile));
|
await writeFileWithLock(pyNotifyFile, await fs.readFile(sampleNotifyPyFile));
|
||||||
|
|
||||||
if (!scriptNotifyJsFileExist) {
|
if (!scriptNotifyJsFileExist) {
|
||||||
await fs.writeFile(
|
await writeFileWithLock(
|
||||||
scriptNotifyJsFile,
|
scriptNotifyJsFile,
|
||||||
await fs.readFile(sampleNotifyJsFile),
|
await fs.readFile(sampleNotifyJsFile),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!scriptNotifyPyFileExist) {
|
if (!scriptNotifyPyFileExist) {
|
||||||
await fs.writeFile(
|
await writeFileWithLock(
|
||||||
scriptNotifyPyFile,
|
scriptNotifyPyFile,
|
||||||
await fs.readFile(sampleNotifyPyFile),
|
await fs.readFile(sampleNotifyPyFile),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!TaskBeforeFileExist) {
|
if (!TaskBeforeFileExist) {
|
||||||
await fs.writeFile(TaskBeforeFile, await fs.readFile(sampleTaskShellFile));
|
await writeFileWithLock(TaskBeforeFile, await fs.readFile(sampleTaskShellFile));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!TaskBeforeJsFileExist) {
|
if (!TaskBeforeJsFileExist) {
|
||||||
await fs.writeFile(
|
await writeFileWithLock(
|
||||||
TaskBeforeJsFile,
|
TaskBeforeJsFile,
|
||||||
'// The JavaScript code that executes before the JavaScript task execution will execute.',
|
'// The JavaScript code that executes before the JavaScript task execution will execute.',
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!TaskBeforePyFileExist) {
|
if (!TaskBeforePyFileExist) {
|
||||||
await fs.writeFile(
|
await writeFileWithLock(
|
||||||
TaskBeforePyFile,
|
TaskBeforePyFile,
|
||||||
'# The Python code that executes before the Python task execution will execute.',
|
'# The Python code that executes before the Python task execution will execute.',
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!TaskAfterFileExist) {
|
if (!TaskAfterFileExist) {
|
||||||
await fs.writeFile(TaskAfterFile, await fs.readFile(sampleTaskShellFile));
|
await writeFileWithLock(TaskAfterFile, await fs.readFile(sampleTaskShellFile));
|
||||||
}
|
}
|
||||||
|
|
||||||
Logger.info('✌️ Init file down');
|
Logger.info('✌️ Init file down');
|
||||||
|
|
|
@ -21,6 +21,7 @@ import { spawn } from 'cross-spawn';
|
||||||
import dayjs from 'dayjs';
|
import dayjs from 'dayjs';
|
||||||
import pickBy from 'lodash/pickBy';
|
import pickBy from 'lodash/pickBy';
|
||||||
import omit from 'lodash/omit';
|
import omit from 'lodash/omit';
|
||||||
|
import { writeFileWithLock } from '../shared/utils';
|
||||||
|
|
||||||
@Service()
|
@Service()
|
||||||
export default class CronService {
|
export default class CronService {
|
||||||
|
@ -601,7 +602,7 @@ export default class CronService {
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
await fs.writeFile(config.crontabFile, crontab_string);
|
await writeFileWithLock(config.crontabFile, crontab_string);
|
||||||
|
|
||||||
execSync(`crontab ${config.crontabFile}`);
|
execSync(`crontab ${config.crontabFile}`);
|
||||||
await CrontabModel.update({ saved: true }, { where: {} });
|
await CrontabModel.update({ saved: true }, { where: {} });
|
||||||
|
|
|
@ -13,6 +13,7 @@ import {
|
||||||
} from '../data/env';
|
} from '../data/env';
|
||||||
import groupBy from 'lodash/groupBy';
|
import groupBy from 'lodash/groupBy';
|
||||||
import { FindOptions, Op } from 'sequelize';
|
import { FindOptions, Op } from 'sequelize';
|
||||||
|
import { writeFileWithLock } from '../shared/utils';
|
||||||
|
|
||||||
@Service()
|
@Service()
|
||||||
export default class EnvService {
|
export default class EnvService {
|
||||||
|
@ -225,8 +226,8 @@ export default class EnvService {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
await fs.writeFile(config.envFile, env_string);
|
await writeFileWithLock(config.envFile, env_string);
|
||||||
await fs.writeFile(config.jsEnvFile, js_env_string);
|
await writeFileWithLock(config.jsEnvFile, js_env_string);
|
||||||
await fs.writeFile(config.pyEnvFile, py_env_string);
|
await writeFileWithLock(config.pyEnvFile, py_env_string);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,6 +7,7 @@ import { Subscription } from '../data/subscription';
|
||||||
import { formatUrl } from '../config/subscription';
|
import { formatUrl } from '../config/subscription';
|
||||||
import config from '../config';
|
import config from '../config';
|
||||||
import { fileExist, rmPath } from '../config/util';
|
import { fileExist, rmPath } from '../config/util';
|
||||||
|
import { writeFileWithLock } from '../shared/utils';
|
||||||
|
|
||||||
@Service()
|
@Service()
|
||||||
export default class SshKeyService {
|
export default class SshKeyService {
|
||||||
|
@ -25,13 +26,12 @@ export default class SshKeyService {
|
||||||
if (_exist) {
|
if (_exist) {
|
||||||
config = await fs.readFile(this.sshConfigFilePath, { encoding: 'utf-8' });
|
config = await fs.readFile(this.sshConfigFilePath, { encoding: 'utf-8' });
|
||||||
} else {
|
} else {
|
||||||
await fs.writeFile(this.sshConfigFilePath, '');
|
await writeFileWithLock(this.sshConfigFilePath, '');
|
||||||
}
|
}
|
||||||
if (!config.includes(this.sshConfigHeader)) {
|
if (!config.includes(this.sshConfigHeader)) {
|
||||||
await fs.writeFile(
|
await writeFileWithLock(
|
||||||
this.sshConfigFilePath,
|
this.sshConfigFilePath,
|
||||||
`${this.sshConfigHeader}\n\n${config}`,
|
`${this.sshConfigHeader}\n\n${config}`,
|
||||||
{ encoding: 'utf-8' },
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -41,10 +41,14 @@ export default class SshKeyService {
|
||||||
key: string,
|
key: string,
|
||||||
): Promise<void> {
|
): Promise<void> {
|
||||||
try {
|
try {
|
||||||
await fs.writeFile(path.join(this.sshPath, alias), `${key}${os.EOL}`, {
|
await writeFileWithLock(
|
||||||
|
path.join(this.sshPath, alias),
|
||||||
|
`${key}${os.EOL}`,
|
||||||
|
{
|
||||||
encoding: 'utf8',
|
encoding: 'utf8',
|
||||||
mode: '400',
|
mode: '400',
|
||||||
});
|
},
|
||||||
|
);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
this.logger.error('生成私钥文件失败', error);
|
this.logger.error('生成私钥文件失败', error);
|
||||||
}
|
}
|
||||||
|
@ -74,12 +78,9 @@ export default class SshKeyService {
|
||||||
this.sshPath,
|
this.sshPath,
|
||||||
alias,
|
alias,
|
||||||
)}\n StrictHostKeyChecking no\n${proxyStr}`;
|
)}\n StrictHostKeyChecking no\n${proxyStr}`;
|
||||||
await fs.writeFile(
|
await writeFileWithLock(
|
||||||
`${path.join(this.sshPath, `${alias}.config`)}`,
|
`${path.join(this.sshPath, `${alias}.config`)}`,
|
||||||
config,
|
config,
|
||||||
{
|
|
||||||
encoding: 'utf8',
|
|
||||||
},
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -102,7 +103,11 @@ export default class SshKeyService {
|
||||||
await this.generateSingleSshConfig(alias, host, proxy);
|
await this.generateSingleSshConfig(alias, host, proxy);
|
||||||
}
|
}
|
||||||
|
|
||||||
public async removeSSHKey(alias: string, host: string, proxy?: string): Promise<void> {
|
public async removeSSHKey(
|
||||||
|
alias: string,
|
||||||
|
host: string,
|
||||||
|
proxy?: string,
|
||||||
|
): Promise<void> {
|
||||||
await this.removePrivateKeyFile(alias);
|
await this.removePrivateKeyFile(alias);
|
||||||
await this.removeSshConfig(alias);
|
await this.removeSshConfig(alias);
|
||||||
}
|
}
|
||||||
|
|
27
back/shared/utils.ts
Normal file
27
back/shared/utils.ts
Normal file
|
@ -0,0 +1,27 @@
|
||||||
|
import { lock } from 'proper-lockfile';
|
||||||
|
import { writeFile, open } from 'fs/promises';
|
||||||
|
import { fileExist } from '../config/util';
|
||||||
|
|
||||||
|
export async function writeFileWithLock(
|
||||||
|
path: string,
|
||||||
|
content: string | Buffer,
|
||||||
|
options: Parameters<typeof writeFile>[2] = {},
|
||||||
|
) {
|
||||||
|
if (typeof options === 'string') {
|
||||||
|
options = { encoding: options };
|
||||||
|
}
|
||||||
|
if (!(await fileExist(path))) {
|
||||||
|
const fileHandle = await open(path, 'w');
|
||||||
|
fileHandle.close();
|
||||||
|
}
|
||||||
|
const release = await lock(path, {
|
||||||
|
retries: {
|
||||||
|
retries: 10,
|
||||||
|
factor: 2,
|
||||||
|
minTimeout: 100,
|
||||||
|
maxTimeout: 3000,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
await writeFile(path, content, { encoding: 'utf8', ...options });
|
||||||
|
await release();
|
||||||
|
}
|
|
@ -6,6 +6,7 @@ import fs from 'fs';
|
||||||
import config from './config';
|
import config from './config';
|
||||||
import path from 'path';
|
import path from 'path';
|
||||||
import os from 'os';
|
import os from 'os';
|
||||||
|
import { writeFileWithLock } from './shared/utils';
|
||||||
|
|
||||||
const tokenFile = path.join(config.configPath, 'token.json');
|
const tokenFile = path.join(config.configPath, 'token.json');
|
||||||
|
|
||||||
|
@ -25,16 +26,7 @@ async function getToken() {
|
||||||
}
|
}
|
||||||
|
|
||||||
async function writeFile(data: any) {
|
async function writeFile(data: any) {
|
||||||
return new Promise<void>((resolve, reject) => {
|
await writeFileWithLock(tokenFile, `${JSON.stringify(data)}${os.EOL}`);
|
||||||
fs.writeFile(
|
|
||||||
tokenFile,
|
|
||||||
`${JSON.stringify(data)}${os.EOL}`,
|
|
||||||
{ encoding: 'utf8' },
|
|
||||||
() => {
|
|
||||||
resolve();
|
|
||||||
},
|
|
||||||
);
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
getToken();
|
getToken();
|
||||||
|
|
|
@ -103,7 +103,8 @@
|
||||||
"request-ip": "3.3.0",
|
"request-ip": "3.3.0",
|
||||||
"ip2region": "2.3.0",
|
"ip2region": "2.3.0",
|
||||||
"keyv": "^5.2.3",
|
"keyv": "^5.2.3",
|
||||||
"@keyv/sqlite": "^4.0.1"
|
"@keyv/sqlite": "^4.0.1",
|
||||||
|
"proper-lockfile": "^4.1.2"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"moment": "2.30.1",
|
"moment": "2.30.1",
|
||||||
|
@ -138,6 +139,7 @@
|
||||||
"@types/sockjs-client": "^1.5.1",
|
"@types/sockjs-client": "^1.5.1",
|
||||||
"@types/uuid": "^8.3.4",
|
"@types/uuid": "^8.3.4",
|
||||||
"@types/request-ip": "0.0.41",
|
"@types/request-ip": "0.0.41",
|
||||||
|
"@types/proper-lockfile": "^4.1.4",
|
||||||
"@uiw/codemirror-extensions-langs": "^4.21.9",
|
"@uiw/codemirror-extensions-langs": "^4.21.9",
|
||||||
"@uiw/react-codemirror": "^4.21.9",
|
"@uiw/react-codemirror": "^4.21.9",
|
||||||
"@umijs/max": "^4.3.36",
|
"@umijs/max": "^4.3.36",
|
||||||
|
|
|
@ -1,5 +1,9 @@
|
||||||
lockfileVersion: '6.0'
|
lockfileVersion: '6.0'
|
||||||
|
|
||||||
|
settings:
|
||||||
|
autoInstallPeers: true
|
||||||
|
excludeLinksFromLockfile: false
|
||||||
|
|
||||||
overrides:
|
overrides:
|
||||||
sqlite3: git+https://github.com/whyour/node-sqlite3.git#v1.0.3
|
sqlite3: git+https://github.com/whyour/node-sqlite3.git#v1.0.3
|
||||||
|
|
||||||
|
@ -97,6 +101,9 @@ dependencies:
|
||||||
p-queue-cjs:
|
p-queue-cjs:
|
||||||
specifier: 7.3.4
|
specifier: 7.3.4
|
||||||
version: 7.3.4
|
version: 7.3.4
|
||||||
|
proper-lockfile:
|
||||||
|
specifier: ^4.1.2
|
||||||
|
version: 4.1.2
|
||||||
protobufjs:
|
protobufjs:
|
||||||
specifier: ^7.4.0
|
specifier: ^7.4.0
|
||||||
version: 7.4.0
|
version: 7.4.0
|
||||||
|
@ -201,6 +208,9 @@ devDependencies:
|
||||||
'@types/nodemailer':
|
'@types/nodemailer':
|
||||||
specifier: ^6.4.4
|
specifier: ^6.4.4
|
||||||
version: 6.4.17
|
version: 6.4.17
|
||||||
|
'@types/proper-lockfile':
|
||||||
|
specifier: ^4.1.4
|
||||||
|
version: 4.1.4
|
||||||
'@types/qrcode.react':
|
'@types/qrcode.react':
|
||||||
specifier: ^1.0.2
|
specifier: ^1.0.2
|
||||||
version: 1.0.5
|
version: 1.0.5
|
||||||
|
@ -4634,6 +4644,12 @@ packages:
|
||||||
resolution: {integrity: sha512-hCZTSvwbzWGvhqxp/RqVqwU999pBf2vp7hzIjiYOsl8wqOmUxkQ6ddw1cV3l8811+kdUFus/q4d1Y3E3SyEifA==}
|
resolution: {integrity: sha512-hCZTSvwbzWGvhqxp/RqVqwU999pBf2vp7hzIjiYOsl8wqOmUxkQ6ddw1cV3l8811+kdUFus/q4d1Y3E3SyEifA==}
|
||||||
dev: true
|
dev: true
|
||||||
|
|
||||||
|
/@types/proper-lockfile@4.1.4:
|
||||||
|
resolution: {integrity: sha512-uo2ABllncSqg9F1D4nugVl9v93RmjxF6LJzQLMLDdPaXCUIDPeOJ21Gbqi43xNKzBi/WQ0Q0dICqufzQbMjipQ==}
|
||||||
|
dependencies:
|
||||||
|
'@types/retry': 0.12.5
|
||||||
|
dev: true
|
||||||
|
|
||||||
/@types/qrcode.react@1.0.5:
|
/@types/qrcode.react@1.0.5:
|
||||||
resolution: {integrity: sha512-BghPtnlwvrvq8QkGa1H25YnN+5OIgCKFuQruncGWLGJYOzeSKiix/4+B9BtfKF2wf5ja8yfyWYA3OXju995G8w==}
|
resolution: {integrity: sha512-BghPtnlwvrvq8QkGa1H25YnN+5OIgCKFuQruncGWLGJYOzeSKiix/4+B9BtfKF2wf5ja8yfyWYA3OXju995G8w==}
|
||||||
dependencies:
|
dependencies:
|
||||||
|
@ -4683,6 +4699,10 @@ packages:
|
||||||
'@types/node': 17.0.45
|
'@types/node': 17.0.45
|
||||||
dev: false
|
dev: false
|
||||||
|
|
||||||
|
/@types/retry@0.12.5:
|
||||||
|
resolution: {integrity: sha512-3xSjTp3v03X/lSQLkczaN9UIEwJMoMCA1+Nb5HfbJEQWogdeQIyVtTvxPXDQjZ5zws8rFQfVfRdz03ARihPJgw==}
|
||||||
|
dev: true
|
||||||
|
|
||||||
/@types/semver@7.5.8:
|
/@types/semver@7.5.8:
|
||||||
resolution: {integrity: sha512-I8EUhyrgfLrcTkzV3TSsGyl1tSuPrEDzr0yd5m90UgNxQkyDXULk3b6MlQqTCpZpNtWe1K0hzclnZkTcLBe2UQ==}
|
resolution: {integrity: sha512-I8EUhyrgfLrcTkzV3TSsGyl1tSuPrEDzr0yd5m90UgNxQkyDXULk3b6MlQqTCpZpNtWe1K0hzclnZkTcLBe2UQ==}
|
||||||
dev: true
|
dev: true
|
||||||
|
@ -12466,6 +12486,14 @@ packages:
|
||||||
react-is: 16.13.1
|
react-is: 16.13.1
|
||||||
dev: true
|
dev: true
|
||||||
|
|
||||||
|
/proper-lockfile@4.1.2:
|
||||||
|
resolution: {integrity: sha512-TjNPblN4BwAWMXU8s9AEz4JmQxnD1NNL7bNOY/AKUzyamc379FWASUhc/K1pL2noVb+XmZKLL68cjzLsiOAMaA==}
|
||||||
|
dependencies:
|
||||||
|
graceful-fs: 4.2.11
|
||||||
|
retry: 0.12.0
|
||||||
|
signal-exit: 3.0.7
|
||||||
|
dev: false
|
||||||
|
|
||||||
/protobufjs@7.4.0:
|
/protobufjs@7.4.0:
|
||||||
resolution: {integrity: sha512-mRUWCc3KUU4w1jU8sGxICXH/gNS94DvI1gxqDvBzhj1JpcsimQkYiOJfwsPUykUI5ZaspFbSgmBLER8IrQ3tqw==}
|
resolution: {integrity: sha512-mRUWCc3KUU4w1jU8sGxICXH/gNS94DvI1gxqDvBzhj1JpcsimQkYiOJfwsPUykUI5ZaspFbSgmBLER8IrQ3tqw==}
|
||||||
engines: {node: '>=12.0.0'}
|
engines: {node: '>=12.0.0'}
|
||||||
|
@ -14041,7 +14069,6 @@ packages:
|
||||||
engines: {node: '>= 4'}
|
engines: {node: '>= 4'}
|
||||||
requiresBuild: true
|
requiresBuild: true
|
||||||
dev: false
|
dev: false
|
||||||
optional: true
|
|
||||||
|
|
||||||
/reusify@1.0.4:
|
/reusify@1.0.4:
|
||||||
resolution: {integrity: sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==}
|
resolution: {integrity: sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==}
|
||||||
|
@ -16174,7 +16201,3 @@ packages:
|
||||||
- encoding
|
- encoding
|
||||||
- supports-color
|
- supports-color
|
||||||
dev: false
|
dev: false
|
||||||
|
|
||||||
settings:
|
|
||||||
autoInstallPeers: true
|
|
||||||
excludeLinksFromLockfile: false
|
|
||||||
|
|
|
@ -3,9 +3,6 @@
|
||||||
"target": "es2017",
|
"target": "es2017",
|
||||||
"lib": ["ESNext"],
|
"lib": ["ESNext"],
|
||||||
"typeRoots": ["./node_modules/celebrate/lib", "./node_modules/@types"],
|
"typeRoots": ["./node_modules/celebrate/lib", "./node_modules/@types"],
|
||||||
"paths": {
|
|
||||||
"@/*": ["./back/*"]
|
|
||||||
},
|
|
||||||
"allowSyntheticDefaultImports": true,
|
"allowSyntheticDefaultImports": true,
|
||||||
"experimentalDecorators": true,
|
"experimentalDecorators": true,
|
||||||
"emitDecoratorMetadata": true,
|
"emitDecoratorMetadata": true,
|
||||||
|
|
|
@ -22,10 +22,6 @@
|
||||||
"allowJs": true,
|
"allowJs": true,
|
||||||
"noEmit": false
|
"noEmit": false
|
||||||
},
|
},
|
||||||
"include": ["src/**/*", ".umirc.ts", "typings.d.ts", "back/**/*"],
|
"include": ["src/**/*", ".umirc.ts", "typings.d.ts"],
|
||||||
"exclude": [
|
"exclude": ["node_modules", "static", "data"]
|
||||||
"node_modules",
|
|
||||||
"static",
|
|
||||||
"data",
|
|
||||||
]
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue
Block a user