Ohne Bibliothek
Alles, was ein Bot tut, ist einfaches HTTPS und WebSocket. Diese Seite zeigt die Aufrufe, damit du einen Bot in jeder Sprache schreiben kannst.
Das brauchst du
Einen HTTP-Client und einen WebSocket-Client. curl reicht für die ersten Schritte. YOUR_BOT_TOKEN steht für dein Token.
Eine Anfrage stellen
curl "https://api.zrzur.com/users/@me" -H "x-bot-token: YOUR_BOT_TOKEN"_id in der Antwort ist die ID deines Bots und auch seine Anwendungs-ID.
Anfragetexte sind JSON, mit content-type: application/json. Antworten sind JSON oder leer mit 204.
Eine Nachricht senden
curl -X POST "https://api.zrzur.com/channels/CHANNEL_ID/messages" \
-H "x-bot-token: YOUR_BOT_TOKEN" \
-H "content-type: application/json" \
-d '{ "content": "Hello!" }'Eine Datei hochladen
curl -X POST "https://cdn.zrzur.com/attachments" \
-H "x-bot-token: YOUR_BOT_TOKEN" \
-F "[email protected];type=text/csv"Die Antwort ist { "id": "FILE_ID" }. Sende sie in attachments einer Nachricht.
Die ganze Schleife
PUT /applications/{application_id}/commandsmit deinen Befehlen.- Öffne
wss://events.zrzur.com/?version=1&format=json. - Sende
{ "type": "Authenticate", "token": "YOUR_BOT_TOKEN", "intents": 33 }. - Sende alle 20 Sekunden
{ "type": "Ping", "data": 1 }. - Für jedes Paket: Ist
typegleichBulk, behandle jeden Eintrag vonv. - Bei
InteractionCreate, innerhalb von 3 Sekunden,POST /interactions/{interaction_id}/{token}/callback. - Wenn der Socket schließt, warte und beginne wieder bei Schritt 2.
Node
Node 22 hat fetch und WebSocket eingebaut. Das ist ein vollständiger Bot in einer Datei:
// Hello World without any library: Node 22+, fetch and WebSocket only.
//
// ZRZUR_BOT_TOKEN=YOUR_BOT_TOKEN node hello-raw.mjs
const token = process.env.ZRZUR_BOT_TOKEN;
const api = process.env.ZRZUR_API_URL ?? "https://api.zrzur.com";
const ws = process.env.ZRZUR_WS_URL ?? "wss://events.zrzur.com";
if (!token) {
console.error("Set ZRZUR_BOT_TOKEN first.");
process.exit(2);
}
/** An interaction's token is in its path: it must never reach a log */
const masked = (path) =>
path.replace(/(\/interactions\/[^/]+\/)[^/]+/, "$1***");
async function rest(method, path, body) {
const response = await fetch(api + path, {
method,
headers: {
"x-bot-token": token,
...(body ? { "content-type": "application/json" } : {}),
},
body: body ? JSON.stringify(body) : undefined,
});
if (!response.ok)
throw new Error(
`${method} ${masked(path)}: ${response.status} ${await response.text()}`,
);
return response.status === 204 ? null : response.json();
}
// 1. Who am I? A bot's application id is its user id.
const me = await rest("GET", "/users/@me");
// 2. Register the global /hello command (PUT replaces the whole list).
await rest("PUT", `/applications/${me._id}/commands`, [
{ name: "hello", description: "Say hello" },
]);
// 3. Connect to the gateway and answer interactions.
const socket = new WebSocket(`${ws}/?version=1&format=json`);
// intents 33 = SERVERS (1) + INTERACTIONS (32): commands, nothing else
socket.addEventListener("open", () =>
socket.send(JSON.stringify({ type: "Authenticate", token, intents: 33 })),
);
async function handle(event) {
if (event.type === "Ready") console.log(`ready as ${me.username}`);
if (
event.type === "InteractionCreate" &&
event.interaction.command?.name === "hello"
) {
const { _id, token: interactionToken } = event.interaction;
// answer within 3 seconds
await rest("POST", `/interactions/${_id}/${interactionToken}/callback`, {
type: "Message",
data: { content: "Hello from Zrzur!" },
});
}
}
socket.addEventListener("message", ({ data }) => {
const event = JSON.parse(data);
// several events can arrive together in one Bulk packet
for (const item of event.type === "Bulk" ? event.v : [event])
handle(item).catch(console.error);
});
// keep the connection alive
setInterval(
() => socket.send(JSON.stringify({ type: "Ping", data: Date.now() })),
20_000,
);
Der vollständige Bot ergänzt Ratenlimits, Wiederholungen, Wiederverbindung und gespeicherte Daten.
Python
Python braucht das Paket websockets (pip install websockets). Für HTTP reicht die Standardbibliothek.
import asyncio, json, os, urllib.request
import websockets
TOKEN = os.environ["ZRZUR_BOT_TOKEN"]
API = "https://api.zrzur.com"
def rest(method, path, body=None):
request = urllib.request.Request(
API + path,
method=method,
data=json.dumps(body).encode() if body is not None else None,
headers={"x-bot-token": TOKEN, "content-type": "application/json"},
)
with urllib.request.urlopen(request) as response:
data = response.read()
return json.loads(data) if data else None
async def main():
me = rest("GET", "/users/@me")
rest("PUT", f"/applications/{me['_id']}/commands",
[{"name": "hello", "description": "Say hello"}])
async with websockets.connect("wss://events.zrzur.com/?version=1&format=json") as socket:
await socket.send(json.dumps({"type": "Authenticate", "token": TOKEN, "intents": 33}))
async def ping():
while True:
await asyncio.sleep(20)
await socket.send(json.dumps({"type": "Ping", "data": 1}))
asyncio.create_task(ping())
async for raw in socket:
packet = json.loads(raw)
for event in packet["v"] if packet["type"] == "Bulk" else [packet]:
if event["type"] == "Ready":
print("ready")
if event["type"] == "InteractionCreate":
i = event["interaction"]
rest("POST", f"/interactions/{i['_id']}/{i['token']}/callback",
{"type": "Message", "data": {"content": "Hello from Python!"}})
asyncio.run(main())Diese kurze Fassung verbindet nicht neu. Ergänze die Schleife aus Gateway.
Maschinenlesbare Beschreibungen
| Adresse | Was |
|---|---|
GET /openapi.json | Jede REST-Route als OpenAPI 3 |
GET /gateway/schema | Jedes Gateway-Ereignis als JSON Schema |
GET / | Adressen und Limits dieses Servers |
Erzeuge daraus einen Client in deiner Sprache.