rule34 implementation and code upgrades

This commit is contained in:
fzzinchemical
2025-04-15 17:55:29 +02:00
parent c32b80e87b
commit f9a8650243
4 changed files with 88 additions and 71 deletions

4
deno.lock generated
View File

@@ -1,6 +1,7 @@
{ {
"version": "4", "version": "4",
"specifiers": { "specifiers": {
"jsr:@melvdouc/xml-parser@*": "0.1.1",
"jsr:@std/dotenv@0.225.3": "0.225.3", "jsr:@std/dotenv@0.225.3": "0.225.3",
"jsr:@std/fmt@^1.0.5": "1.0.6", "jsr:@std/fmt@^1.0.5": "1.0.6",
"jsr:@std/fs@^1.0.11": "1.0.15", "jsr:@std/fs@^1.0.11": "1.0.15",
@@ -10,6 +11,9 @@
"npm:discord.js@14.18.0": "14.18.0" "npm:discord.js@14.18.0": "14.18.0"
}, },
"jsr": { "jsr": {
"@melvdouc/xml-parser@0.1.1": {
"integrity": "5c79d37c6471cb74efb344988317270b57b4f181decb873e441453db42eb6e5f"
},
"@std/dotenv@0.225.3": { "@std/dotenv@0.225.3": {
"integrity": "a95e5b812c27b0854c52acbae215856d9cce9d4bbf774d938c51d212711e8d4a" "integrity": "a95e5b812c27b0854c52acbae215856d9cce9d4bbf774d938c51d212711e8d4a"
}, },

View File

@@ -1,6 +1,6 @@
//TODO Add optional extensions like limit at Posts with tags etc. //TODO Add optional extensions like limit at Posts with tags etc.
import * as xml_parser from "jsr:@melvdouc/xml-parser"; import * as xml_parser from "jsr:@melvdouc/xml-parser";
import { requestRaw, requestJSON } from "@root/structures/apiRequest.ts"; import { requestRaw } from "@root/structures/apiRequest.ts";
export type ImageResponse = { export type ImageResponse = {
preview_url: string; preview_url: string;

View File

@@ -1,7 +1,7 @@
import { ChatInputCommandInteraction, SlashCommandBuilder } from "@discordjs"; import { ChatInputCommandInteraction, SlashCommandBuilder } from "@discordjs";
import { requestWorker } from "@root/plugins/rule34/plugin.ts";
// import { drop, help, requestWorker } from "./plugin.ts"; // import { drop, help, requestWorker } from "./plugin.ts";
import { logMessage } from "@root/logging.ts";
import { defaultString } from "@root/defaultString.ts";
// export async function rule34MessageHandler(message: Message) { // export async function rule34MessageHandler(message: Message) {
// const command = message.content.trim().split(" ").slice(1).join(" "); // const command = message.content.trim().split(" ").slice(1).join(" ");
@@ -28,6 +28,7 @@ import { defaultString } from "@root/defaultString.ts";
// } // }
// } // }
export const commands = [ export const commands = [
{ {
data: new SlashCommandBuilder() data: new SlashCommandBuilder()
@@ -38,9 +39,47 @@ export const commands = [
subcommand subcommand
.setName("drop") .setName("drop")
.setDescription("Drops one or multiple images using the rule34 API.") .setDescription("Drops one or multiple images using the rule34 API.")
), .addStringOption((option) => option
.setName("limit")
.setDescription("Post limitation")
)
.addStringOption((option) =>
option
.setName("tags")
.setDescription("Tags to add to query")
)
.addStringOption((option) =>
option
.setName("page")
.setDescription("Which page to query")
)
.addStringOption((option) =>
option
.setName("pid")
.setDescription("Which page to query")
)
),
async execute(interaction: ChatInputCommandInteraction) { async execute(interaction: ChatInputCommandInteraction) {
await interaction.reply(`VIOLENCE!`); const limit = interaction.options.getString("limit")
const tags = interaction.options.getString("tags")
const page = interaction.options.getString("page")
const pid = interaction.options.getString("pid")
if (limit === null && tags === null && page === null && pid === null) {
await interaction.reply({
embeds: await requestWorker({
limit: "1"
})
})
} else {
await interaction.reply({
embeds: await requestWorker({
limit: limit,
tags: tags,
page: page,
pid: pid,
}),
})
}
}, },
}, },
]; ];

View File

@@ -1,12 +1,13 @@
import { assert } from "@std/assert/assert";
import { requestJSON } from "@root/structures/apiRequest.ts"; import { requestJSON } from "@root/structures/apiRequest.ts";
import { ImageResponse, postUrl } from "./api.ts"; import { ImageResponse, postUrl } from "./api.ts";
import { EmbedBuilder } from "@discordjs";
const keys = ["limit", "id", "pid", "tags"] as const; export type PostRequestParameters = {
type PostKeys = typeof keys[number]; limit?: string| null| undefined,
id?: string| null| undefined,
function isKey(key: string): key is PostKeys { pid?: string| null| undefined,
return keys.includes(key as any); tags?: string| null| undefined,
page?: string| null| undefined,
} }
// export async function drop() { // export async function drop() {
@@ -36,67 +37,40 @@ function isKey(key: string): key is PostKeys {
// } // }
// } // }
// export async function requestWorker(requestString: string) { export async function requestWorker(postRequestParams: PostRequestParameters) {
// try { const embeds = [];
// const response = await requestJSON<ImageResponse[]>( try {
// generateRequestURL(requestString), const response = await requestJSON<ImageResponse[]>(
// ); generateRequestURL(postRequestParams),
// const stack: Embed[] = []; );
// for (const img of response) { for (const post of response) {
// stack.push( embeds.push(
// new Embed( new EmbedBuilder()
// `ID: ${img.id}`, .setTitle(post.id.toString())
// img.sample_url, .setURL(post.file_url)
// new EmbedAuthor(img.owner), .setAuthor(
// // [new EmbedField("Tags", img.tags, true)], {
// new EmbedImage(img.file_url, img.height, img.width), name: post.owner,
// ), },
// ); )
// } .setImage(post.preview_url),
// return stack; );
// } catch (e) { }
// console.error((e as Error).message); } catch (e) {
// return []; console.error((e as Error).message);
// } return [];
// }
//TODO: get help in form of a nice beautiful format
export function help() {
return "WIP";
}
export function requestParser(requestString: string) {
const res = requestString.match(/\[([\s*w+:\s*[\d+|\w+,]+)\]/g);
const map = new Map<PostKeys, string>();
if (res !== null) {
res[0]
.split(",")
.forEach((param) => {
const match = param.match(/\s*(\w+)\s*:\s*([\w+,+]+)/);
console.debug({ match });
if (match !== null) {
if (match[1] === undefined || match[2] === undefined) {
throw Error("Unreachable");
}
if (!isKey(match[1])) throw Error(`Key: ${match[1]} is not a Key!`);
map.set(match[1], match[2]);
} else {
throw Error(`match returned null in param = ${Deno.inspect(param)}`);
}
});
} else {
throw Error("Request String had some major issues chief");
} }
return map; return embeds;
} }
// + is replaced with a space... this is pain export function generateRequestURL(postRequestParams: PostRequestParameters) {
// see percent code + === 2B const postCpy = new URL(postUrl);
export function generateRequestURL(requestString: string) { const parameterStrings: string[] = []
const postCpy = new URL(postUrl.toString());
for (const [k, v] of requestParser(requestString)) { Object.entries(postRequestParams).forEach(([k, v]) => {
postCpy.searchParams.append(k, v); if (v !== null) {
} parameterStrings.push(`&${k}=${v}`)
return postCpy.href.toString().replaceAll("%2B", "+"); }
});
return postCpy.href + parameterStrings.join('');
} }