koishi-plugin-nmc-radar 1.3.0 → 1.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/index.d.ts +6 -2
- package/lib/index.js +45 -22
- package/package.json +1 -1
package/lib/index.d.ts
CHANGED
|
@@ -1,10 +1,14 @@
|
|
|
1
|
-
import type { Awaitable, Context } from 'koishi';
|
|
1
|
+
import type { Awaitable, Context, Dict } from 'koishi';
|
|
2
2
|
import { h, Schema } from 'koishi';
|
|
3
3
|
export declare const name = "nmc-radar";
|
|
4
4
|
export declare const inject: {
|
|
5
5
|
optional: string[];
|
|
6
6
|
};
|
|
7
|
-
|
|
7
|
+
interface Product {
|
|
8
|
+
url: string;
|
|
9
|
+
slug: string;
|
|
10
|
+
}
|
|
11
|
+
type Resolver = (products: Product[], options: Dict) => Awaitable<h>;
|
|
8
12
|
declare const resolvers: Record<string, Resolver>;
|
|
9
13
|
export interface Config {
|
|
10
14
|
defaultResolver: keyof typeof resolvers;
|
package/lib/index.js
CHANGED
|
@@ -36,6 +36,7 @@ __export(src_exports, {
|
|
|
36
36
|
name: () => name
|
|
37
37
|
});
|
|
38
38
|
module.exports = __toCommonJS(src_exports);
|
|
39
|
+
var import_node_buffer = require("node:buffer");
|
|
39
40
|
var import_promises = require("node:fs/promises");
|
|
40
41
|
var import_node_path = __toESM(require("node:path"));
|
|
41
42
|
var import_jsdom = require("jsdom");
|
|
@@ -325,39 +326,61 @@ var inject = {
|
|
|
325
326
|
optional: ["ffmpeg"]
|
|
326
327
|
};
|
|
327
328
|
var resolvers = {
|
|
328
|
-
img: /* @__PURE__ */ __name((
|
|
329
|
-
|
|
330
|
-
url: /* @__PURE__ */ __name((urls) => import_koishi.h.text(urls[0]), "url"),
|
|
331
|
-
urls: /* @__PURE__ */ __name((urls) => import_koishi.h.text(urls.join("\n")), "urls")
|
|
329
|
+
img: /* @__PURE__ */ __name((products) => (0, import_koishi.h)(import_koishi.h.Fragment, ...products.map((url) => import_koishi.h.img(url.url))), "img"),
|
|
330
|
+
url: /* @__PURE__ */ __name((products) => import_koishi.h.text(products.map((url) => url.url).join("\n")), "url")
|
|
332
331
|
};
|
|
333
332
|
var Config = import_koishi.Schema.object({
|
|
334
333
|
defaultResolver: import_koishi.Schema.union(Object.keys(resolvers)).default("img").description("默认输出类型。")
|
|
335
334
|
});
|
|
336
335
|
function apply(ctx, config) {
|
|
337
|
-
const command = ctx.command("radar <name:string>", "查看雷达图", { checkUnknown: true }).alias("雷达").option("
|
|
336
|
+
const command = ctx.command("radar <name:string>", "查看雷达图", { checkUnknown: true }).alias("雷达").option("name", "--name <name:string> 雷达站名称").option("count", "-n <count:number> 最大输出数量").option("reverse", "-R 反转顺序").option("type", "--type <type:string> 输出类型", { type: Object.keys(resolvers) }).option("type", "--img 输出图片", { value: "img" }).option("type", "--url 输出 URL", { value: "url" }).action(async ({ session, options = {} }, name2) => {
|
|
337
|
+
options.name ??= name2;
|
|
338
338
|
if (!(name2 in radars_default))
|
|
339
339
|
return void session?.send("雷达站不存在,可使用 radar.list 查看所有雷达站。");
|
|
340
|
-
const url = radars_default[
|
|
340
|
+
const url = radars_default[options.name];
|
|
341
341
|
const { window: { document } } = new import_jsdom.JSDOM(await ctx.http.get(url));
|
|
342
342
|
const nodes = document.querySelectorAll("div[data-img]");
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
343
|
+
options.type ??= config.defaultResolver;
|
|
344
|
+
options.count ??= options.type === "img" ? 1 : void 0;
|
|
345
|
+
const products = Array.from(nodes).slice(0, options.count).map((node) => ({
|
|
346
|
+
url: node.dataset.img,
|
|
347
|
+
slug: node.dataset.time.replaceAll(/[/ :]/g, "")
|
|
348
|
+
}));
|
|
349
|
+
options.reverse || products.reverse();
|
|
350
|
+
return await resolvers[options.type](products, options);
|
|
346
351
|
});
|
|
347
352
|
ctx.inject(["ffmpeg"], async (ctx2) => {
|
|
348
|
-
command.option("type", "--gif 输出 GIF 动画", { value: "gif" });
|
|
349
|
-
resolvers.gif = async (
|
|
350
|
-
const baseDir = import_node_path.default.join(ctx2.baseDir, "
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
await (0, import_promises.
|
|
357
|
-
}
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
353
|
+
command.option("type", "--gif 输出 GIF 动画", { value: "gif" }).option("fps", "--fps <fps:number> 帧率", { fallback: 10 }).option("loop", "--loop <loop:number> 循环次数", { fallback: -1 });
|
|
354
|
+
resolvers.gif = async (products, options) => {
|
|
355
|
+
const baseDir = import_node_path.default.join(ctx2.baseDir, "cache", name, options.name);
|
|
356
|
+
const outputPath = import_node_path.default.join(baseDir, [
|
|
357
|
+
`${products[0].slug}+${products[products.length - 1].slug}`,
|
|
358
|
+
`-${options.fps}@${options.loop}.gif`
|
|
359
|
+
].join(""));
|
|
360
|
+
try {
|
|
361
|
+
await (0, import_promises.access)(outputPath);
|
|
362
|
+
} catch {
|
|
363
|
+
await (0, import_promises.mkdir)(baseDir, { recursive: true });
|
|
364
|
+
const filePaths = await Promise.all(products.map(async ({ url, slug }) => {
|
|
365
|
+
const filePath = import_node_path.default.join(baseDir, `${slug}.png`);
|
|
366
|
+
try {
|
|
367
|
+
await (0, import_promises.access)(filePath);
|
|
368
|
+
} catch {
|
|
369
|
+
try {
|
|
370
|
+
const response = await ctx2.http.get(url, { responseType: "stream" });
|
|
371
|
+
await (0, import_promises.writeFile)(filePath, response);
|
|
372
|
+
} catch {
|
|
373
|
+
return void await (0, import_promises.unlink)(filePath);
|
|
374
|
+
}
|
|
375
|
+
}
|
|
376
|
+
return filePath;
|
|
377
|
+
}));
|
|
378
|
+
const buffer = [
|
|
379
|
+
...filePaths.filter(Boolean).flatMap((filePath) => `file '${filePath.replaceAll("\\", "/")}'`)
|
|
380
|
+
].join("\n");
|
|
381
|
+
await ctx2.ffmpeg.builder().input(import_node_buffer.Buffer.from(buffer)).inputOption("-f", "concat").inputOption("-safe", "0").inputOption("-protocol_whitelist", "file,fd").inputOption("-r", options.fps).outputOption("-loop", options.loop).run("file", outputPath);
|
|
382
|
+
}
|
|
383
|
+
return import_koishi.h.img(`file://${outputPath}`);
|
|
361
384
|
};
|
|
362
385
|
});
|
|
363
386
|
command.subcommand(".list", "查看所有雷达站").action(() => Object.keys(radars_default).join(" "));
|