diff --git a/README.md b/README.md
index 96e5ef4..1d67d8d 100644
--- a/README.md
+++ b/README.md
@@ -1,17 +1,12 @@
-# Eris the Bot
-
-[![Website](https://img.shields.io/website?url=https%3A%2F%2Feris.lisq.eu%2F)](https://eris.lisq.eu/)
-![Unique users](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Feris.lisq.eu%2Fapi%2Fstats&query=%24.userCount&label=unique%20users)
-![Generated images](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Feris.lisq.eu%2Fapi%2Fstats&query=%24.imageCount&label=images%20generated)
-![Processed steps](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Feris.lisq.eu%2Fapi%2Fstats&query=%24.stepCount&label=steps%20processed)
-![Painted pixels](https://img.shields.io/badge/dynamic/json?url=https%3A%2F%2Feris.lisq.eu%2Fapi%2Fstats&query=%24.pixelCount&label=pixels%20painted)
+# Nyx the Bot
+Fork of Eris the Bot https://eris.lisq.eu
Telegram bot for generating images from text.
## Requirements
-- [Deno](https://deno.land/)
-- [Stable Diffusion WebUI](https://github.com/AUTOMATIC1111/stable-diffusion-webui/)
+- [Deno](https://deno.land/) (for the bot server)
+- [Stable Diffusion WebUI](https://github.com/AUTOMATIC1111/stable-diffusion-webui/) (for the worker that generates images)
## Options
@@ -20,17 +15,23 @@ You can put these in `.env` file or pass them as environment variables.
- `TG_BOT_TOKEN` - Telegram bot token. Get yours from [@BotFather](https://t.me/BotFather).
Required.
- `DENO_KV_PATH` - [Deno KV](https://deno.land/api?s=Deno.openKv&unstable) database file path. A
- temporary file is used by default.
+ temporary file is used by default. Example: /opt/data/botdata.kv
- `LOG_LEVEL` - [Log level](https://deno.land/std@0.201.0/log/mod.ts?s=LogLevels). Default: `INFO`.
## Running
1. Start Eris: `deno task start`
-2. Visit [Eris WebUI](http://localhost:5999/) and login via Telegram.
+2. Visit [Eris WebUI](http://localhost:8443/) and login via Telegram.
3. Promote yourself to admin in the Eris WebUI.
4. Start Stable Diffusion WebUI: `./webui.sh --api` (in SD WebUI directory)
5. Add a new worker in the Eris WebUI.
+## This fork requires the use of webhooks.
+
+1. You need a reverse Proxy and HTTPS certificate set up that proxies all requests from a domain on port 443 (e.g. nyx.akiru.de) to the backend of this bot (:8443).
+2. Change the Webhook URL to your own one in /mod/bot.ts - There are also console log statements you can uncomment for troubleshooting.
+3. Make sure the DNS and firewall are set up for the webhook to be reachable, because otherwise the bot fails to start.
+
## Codegen
The Stable Diffusion API types are auto-generated. To regenerate them, first start your SD WebUI
@@ -38,8 +39,8 @@ with `--nowebui --api`, and then run `deno task generate`
## Project structure
-- `/api` - Eris API served at `http://localhost:5999/api/`.
+- `/api` - Eris API served at `http://localhost:8443/api/`.
- `/app` - Queue handling and other core processes.
- `/bot` - Handling bot commands and other updates from Telegram API.
-- `/ui` - Eris WebUI frontend files served at `http://localhost:5999/`.
+- `/ui` - Eris WebUI frontend files served at `http://localhost:8443/`.
- `/util` - Utility functions shared by other parts.
diff --git a/api/mod.ts b/api/mod.ts
index d59b472..c20a30a 100644
--- a/api/mod.ts
+++ b/api/mod.ts
@@ -2,11 +2,15 @@ import { route } from "reroute";
import { serveSpa } from "serve_spa";
import { api } from "./serveApi.ts";
import { fromFileUrl } from "std/path/mod.ts";
+// New function that handles the webhook
+import { handleWebhook } from "../bot/mod.ts";
+
export async function serveUi() {
- const server = Deno.serve({ port: 5999 }, (request) =>
+ const server = Deno.serve({ port: 8443 }, (request) =>
route(request, {
"/api/*": (request) => api.fetch(request),
+ "/webhook": handleWebhook, // Create the webhook route handle
"/*": (request) =>
serveSpa(request, {
fsRoot: fromFileUrl(new URL("../ui/", import.meta.url)),
diff --git a/bot/mod.ts b/bot/mod.ts
index 6f7fdda..27b2e8d 100644
--- a/bot/mod.ts
+++ b/bot/mod.ts
@@ -1,7 +1,7 @@
import { Api, Bot, Context, RawApi, session, SessionFlavor } from "grammy";
import { FileFlavor, hydrateFiles } from "grammy_files";
import { hydrateReply, ParseModeFlavor } from "grammy_parse_mode";
-import { run, sequentialize } from "grammy_runner";
+import { sequentialize } from "grammy_runner";
import { error, info, warning } from "std/log/mod.ts";
import { sessions } from "../api/sessionsRoute.ts";
import { formatUserChat } from "../utils/formatUserChat.ts";
@@ -12,6 +12,16 @@ import { img2imgCommand, img2imgQuestion } from "./img2imgCommand.ts";
import { pnginfoCommand, pnginfoQuestion } from "./pnginfoCommand.ts";
import { queueCommand } from "./queueCommand.ts";
import { txt2imgCommand, txt2imgQuestion } from "./txt2imgCommand.ts";
+import { setConfig, getConfig } from "../app/config.ts";
+
+// Set the new configuration
+await setConfig({ maxUserJobs: 1, maxJobs: 500 });
+
+// Fetch the updated configuration
+const updatedConfig = await getConfig();
+
+// Log the updated configuration to the console
+console.log("Updated Configuration:", updatedConfig);
interface SessionData {
chat: ErisChatData;
@@ -107,18 +117,38 @@ bot.use(async (ctx, next) => {
}
});
-bot.api.setMyShortDescription("I can generate furry images from text");
-bot.api.setMyDescription(
- "I can generate furry images from text. " +
- "Send /txt2img to generate an image.",
-);
-bot.api.setMyCommands([
- { command: "txt2img", description: "Generate image from text" },
- { command: "img2img", description: "Generate image from image" },
- { command: "pnginfo", description: "Try to extract prompt from raw file" },
- { command: "queue", description: "Show the current queue" },
- { command: "cancel", description: "Cancel all your requests" },
-]);
+// Wrap the calls in try-catch for error handling
+async function setupBotCommands() {
+ try {
+ await bot.api.setMyShortDescription("Generate furry images in '704x704', '576x832', '832x576'. https://ko-fi.com/nyxthebot https://nyx.akiru.de/");
+ } catch (err) {
+ error(`Failed to set short description: ${err.message}`);
+ }
+
+ try {
+ await bot.api.setMyDescription(
+ "I can generate furry images from text. If you want a different size, use 'Size: 576x832' for example." +
+ "Send /txt2img to generate an image.",
+ );
+ } catch (err) {
+ error(`Failed to set description: ${err.message}`);
+ }
+
+ try {
+ await bot.api.setMyCommands([
+ { command: "txt2img", description: "Generate image from text" },
+ { command: "img2img", description: "Generate image from image" },
+ { command: "pnginfo", description: "Try to extract prompt from raw file" },
+ { command: "queue", description: "Show the current queue" },
+ { command: "cancel", description: "Cancel all your requests" },
+ ]);
+ } catch (err) {
+ error(`Failed to set commands: ${err.message}`);
+ }
+}
+
+// Call the setup function
+setupBotCommands();
bot.command("start", async (ctx) => {
if (ctx.match) {
@@ -173,7 +203,26 @@ bot.command("crash", () => {
throw new Error("Crash command used");
});
-export async function runBot() {
- const runner = run(bot, { runner: { silent: true } });
- await runner.task();
+// Set up the webhook in the telegram API and initialize the bot
+await bot.api.setWebhook('https://nyx.akiru.de/webhook');
+await bot.init();
+
+// Function to handle incoming webhook requests
+export async function handleWebhook(req: Request): Promise