refactor: 统一 dataPath 方法 + 提取格式转换代码

This commit is contained in:
Clansty 2022-10-12 13:07:48 +08:00
parent 4f73fc9f14
commit 3c582e1f9b
5 changed files with 58 additions and 39 deletions

View File

@ -13,8 +13,8 @@ import { execSync } from 'child_process';
import random from '../utils/random';
import fs from 'fs';
import fsP from 'fs/promises';
import path from 'path';
import { Config } from 'oicq/lib/client';
import dataPath from '../helpers/dataPath';
const LOG_LEVEL: LogLevel = 'warn';
@ -77,8 +77,8 @@ export default class OicqClient extends Client {
resolve(client);
}
if (!fs.existsSync(`./data/${params.uin}/device-${params.uin}.json`)) {
await fsP.mkdir(`./data/${params.uin}`, { recursive: true });
if (!fs.existsSync(dataPath(`${params.uin}/device-${params.uin}.json`))) {
await fsP.mkdir(dataPath(params.uin.toString()), { recursive: true });
const device = {
product: 'Q2TG',
@ -97,12 +97,12 @@ export default class OicqClient extends Client {
imei: random.imei(),
};
await fsP.writeFile(`./data/${params.uin}/device-${params.uin}.json`, JSON.stringify(device, null, 0), 'utf-8');
await fsP.writeFile(dataPath(`${params.uin}/device-${params.uin}.json`), JSON.stringify(device, null, 0), 'utf-8');
}
const client = new this(params.uin, {
platform: params.platform,
data_dir: path.resolve('./data'),
data_dir: dataPath(),
log_level: LOG_LEVEL,
ffmpeg_path: process.env.FFMPEG_PATH,
ffprobe_path: process.env.FFPROBE_PATH,

42
src/helpers/convert.ts Normal file
View File

@ -0,0 +1,42 @@
import dataPath from './dataPath';
import fs from 'fs';
import path from 'path';
import sharp from 'sharp';
import { file as createTempFile } from 'tmp-promise';
import fsP from 'fs/promises';
import convertWithFfmpeg from '../encoding/convertWithFfmpeg';
import tgsToGif from '../encoding/tgsToGif';
const CACHE_PATH = dataPath('cache');
fs.mkdirSync(CACHE_PATH, { recursive: true });
// 首先查找缓存,要是缓存中没有的话执行第二个参数的方法转换到缓存的文件
const cachedConvert = async (key: string, convert: (outputPath: string) => Promise<any>) => {
const convertedPath = path.join(CACHE_PATH, key);
if (!fs.existsSync(convertedPath)) {
await convert(convertedPath);
}
return convertedPath;
};
export default {
// webp2png这里 webpData 是方法因为不需要的话就不获取了
png: (key: string, webpData: () => Promise<Buffer | Uint8Array | string>) =>
cachedConvert(key + '.png', async (convertedPath) => {
await sharp(await webpData()).png().toFile(convertedPath);
}),
webm2gif: (key: string, webmData: () => Promise<Buffer | Uint8Array | string>) =>
cachedConvert(key + '.gif', async (convertedPath) => {
const temp = await createTempFile();
await fsP.writeFile(temp.path, await webmData());
await convertWithFfmpeg(temp.path, convertedPath, 'gif');
await temp.cleanup();
}),
tgs2gif: (key: string, tgsData: () => Promise<Buffer | Uint8Array | string>) =>
cachedConvert(key + '.gif', async (convertedPath) => {
const tempTgsPath = path.join(CACHE_PATH, key);
await fsP.writeFile(tempTgsPath, await tgsData());
await tgsToGif(tempTgsPath);
await fsP.rm(tempTgsPath);
}),
};

7
src/helpers/dataPath.ts Normal file
View File

@ -0,0 +1,7 @@
import path from 'path';
const DATA_DIR = process.env.DATA_DIR || path.resolve('./data');
// Wrap of path.join, add base DATA_DIR
export default (...paths: string[]) =>
path.join(DATA_DIR, ...paths);

View File

@ -3,7 +3,6 @@ import Instance from './models/Instance';
import db from './models/db';
(async () => {
process.env.DATA_DIR && process.chdir(process.env.DATA_DIR);
configure({
appenders: {
console: { type: 'console' },

View File

@ -15,18 +15,15 @@ import { file as createTempFile, FileResult } from 'tmp-promise';
import fsP from 'fs/promises';
import eviltransform from 'eviltransform';
import silk from '../encoding/silk';
import fs from 'fs';
import tgsToGif from '../encoding/tgsToGif';
import axios from 'axios';
import { md5Hex } from '../utils/hashing';
import Instance from '../models/Instance';
import { Pair } from '../models/Pair';
import sharp from 'sharp';
import convertWithFfmpeg from '../encoding/convertWithFfmpeg';
import OicqClient from '../client/OicqClient';
import lottie from '../constants/lottie';
import _ from 'lodash';
import emoji from '../constants/emoji';
import convert from '../helpers/convert';
const NOT_CHAINABLE_ELEMENTS = ['flash', 'record', 'video', 'location', 'share', 'json', 'xml', 'poke'];
@ -291,13 +288,7 @@ export default class ForwardService {
message.document?.mimeType?.startsWith('image/')) {
// 将 webp 转换为 png防止 macOS 不识别
if (message.document?.mimeType === 'image/webp') {
const convertedPath = path.resolve(path.join('./data/cache/webp', message.document.id.toString(16) + '.png'));
// 先从缓存中找
if (!fs.existsSync(convertedPath)) {
await fsP.mkdir('./data/cache/webp', { recursive: true });
const webpData = await message.downloadMedia({});
await sharp(webpData).png().toFile(convertedPath);
}
const convertedPath = await convert.png(message.document.id.toString(16), () => message.downloadMedia({}));
chain.push({
type: 'image',
file: convertedPath,
@ -320,15 +311,7 @@ export default class ForwardService {
}
else if (file.mimeType === 'video/webm' || message.gif) {
// 把 webm 转换成 gif
const convertedPath = path.resolve(path.join('./data/cache/webm', message.document.id.toString(16) + '.gif'));
// 先从缓存中找
if (!fs.existsSync(convertedPath)) {
await fsP.mkdir('./data/cache/webm', { recursive: true });
const temp = await createTempFile();
tempFiles.push(temp);
await fsP.writeFile(temp.path, await message.downloadMedia({}));
await convertWithFfmpeg(temp.path, convertedPath, 'gif');
}
const convertedPath = await convert.webm2gif(message.document.id.toString(16), () => message.downloadMedia({}));
chain.push({
type: 'image',
file: convertedPath,
@ -345,19 +328,7 @@ export default class ForwardService {
}
else if (message.sticker) {
// 一定是 tgs
let gifPath: string;
const tempTgsPath = path.resolve(path.join('./data/cache/tgs', message.sticker.id.toString(16)));
// 先从缓存中找
if (fs.existsSync(tempTgsPath + '.gif')) {
gifPath = tempTgsPath + '.gif';
}
else {
await fsP.mkdir('./data/cache/tgs', { recursive: true });
await fsP.writeFile(tempTgsPath, await message.downloadMedia({}));
await tgsToGif(tempTgsPath);
await fsP.rm(tempTgsPath);
gifPath = tempTgsPath + '.gif';
}
const gifPath = await convert.tgs2gif(message.sticker.id.toString(16), () => message.downloadMedia({}));
chain.push({
type: 'image',
file: gifPath,