mirror of
https://github.com/SrIzan10/vinci.git
synced 2026-06-06 01:07:00 +00:00
Compare commits
36 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 045c89a6cb | |||
| 8dcd2de683 | |||
| e3c63632a1 | |||
| a6df2e4f31 | |||
| 502811ca9f | |||
| 58dd540ea9 | |||
| 589f53c65c | |||
| 66594ce8bd | |||
| effbe7d9c5 | |||
| 0e8703629d | |||
| b20a969dee | |||
| b82784608f | |||
| ea1d086fd0 | |||
| b84260901d | |||
| 8ac9c16945 | |||
| 8aeebb1164 | |||
| fa23042c99 | |||
| 2aafce2429 | |||
| 8d5c962049 | |||
| 37d983e150 | |||
| 3b9acf6f29 | |||
| 51ea593bcd | |||
| 8112f232e3 | |||
| 214c35a7e6 | |||
| d208f6b8c7 | |||
| 0b8f23cefd | |||
| c95ceb1539 | |||
| 0654ce2bfd | |||
| b84bd0a250 | |||
| 8005ac0699 | |||
| ecada7600e | |||
| 73e397be5b | |||
| 0f08d35876 | |||
| 116f0be0b2 | |||
| 43c0b40703 | |||
|
|
10aa847aba |
7
.devcontainer/devcontainer.json
Normal file
7
.devcontainer/devcontainer.json
Normal file
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"image": "mcr.microsoft.com/devcontainers/universal:2",
|
||||
"runArgs": ["--device=/dev/net/tun"],
|
||||
"features": {
|
||||
"ghcr.io/tailscale/codespace/tailscale": {}
|
||||
}
|
||||
}
|
||||
9
.dockerignore
Normal file
9
.dockerignore
Normal file
@@ -0,0 +1,9 @@
|
||||
.env*
|
||||
node_modules/
|
||||
json.sqlite
|
||||
dist/
|
||||
*giveaway*
|
||||
.sern
|
||||
/generated/generated/prisma
|
||||
prisma/vinci.db
|
||||
!.env.example
|
||||
33
.env.example
33
.env.example
@@ -1,8 +1,27 @@
|
||||
# THIS IS OUTDATED
|
||||
DISCORD_TOKEN=
|
||||
PREFIX=
|
||||
# Database (before rewrites)
|
||||
MONGODB=
|
||||
# API keys
|
||||
CATAPI=
|
||||
DOGAPI=
|
||||
TWITTER=
|
||||
# request makesweet creator for this
|
||||
MAKESWEET=
|
||||
GENIUS=
|
||||
SPOTIFY_CLIENT=
|
||||
SPOTIFY_SECRET=
|
||||
CF_AI_TOKEN=
|
||||
CF_AI_ACC=
|
||||
# Guild configs
|
||||
GUILDID=
|
||||
SUGGESTIONS_CHANNEL=
|
||||
MODLOGS_CHANNEL=
|
||||
JOINSANDLEAVES_CHANNEL=
|
||||
SOCIALS_CHANNEL=
|
||||
GIVEAWAYS_CHANNEL=
|
||||
MCFORM_CHANNEL=
|
||||
CHATGPT_CHANNEL=
|
||||
T_CHANNEL=
|
||||
|
||||
TOKEN=token
|
||||
PREFIX=v!
|
||||
MONGODB=mongodb://
|
||||
HYPIXEL_API=API_KEY
|
||||
YOURLS_KEY=YOURLS_SIGNATURE
|
||||
YOUTUBE_API=
|
||||
NODE_ENV=development
|
||||
12
.github/workflows/docker.yml
vendored
12
.github/workflows/docker.yml
vendored
@@ -22,10 +22,12 @@ jobs:
|
||||
- name: Check out the repo
|
||||
uses: actions/checkout@v3
|
||||
|
||||
- name: Log in to Sr Izan's container registry
|
||||
- name: Set up Docker Buildx
|
||||
uses: docker/setup-buildx-action@v3
|
||||
|
||||
- name: Log in to Docker Hub
|
||||
uses: docker/login-action@f4ef78c080cd8ba55a85445d5b36e214a81df20a
|
||||
with:
|
||||
registry: containers.srizan.dev
|
||||
username: ${{ secrets.DOCKER_USERNAME }}
|
||||
password: ${{ secrets.DOCKER_PASSWORD }}
|
||||
|
||||
@@ -33,7 +35,7 @@ jobs:
|
||||
id: meta
|
||||
uses: docker/metadata-action@9ec57ed1fcdbf14dcef7dfbe97b2010124a938b7
|
||||
with:
|
||||
images: containers.srizan.dev/vinci
|
||||
images: srizan10/vinci
|
||||
tags: latest
|
||||
|
||||
- name: Build and push Docker image
|
||||
@@ -50,5 +52,5 @@ jobs:
|
||||
AUTH_HEADER: ${{ secrets.WHSERVER_TOKEN }}
|
||||
run: |
|
||||
curl -X POST \
|
||||
-H "Authorization: Bearer $AUTH_HEADER" \
|
||||
https://webhooks.srizan.dev/hooks/vinci
|
||||
-H "Authorization: $AUTH_HEADER" \
|
||||
https://webhooks.srizan.dev/hooks/vinci
|
||||
|
||||
11
.gitignore
vendored
11
.gitignore
vendored
@@ -1,6 +1,11 @@
|
||||
.env
|
||||
.env.dev
|
||||
.env*
|
||||
node_modules/
|
||||
json.sqlite
|
||||
dist/
|
||||
*giveaway*
|
||||
*giveaway*
|
||||
.sern
|
||||
/generated/generated/prisma
|
||||
src/utils/db/dict.db
|
||||
prisma/vinci.db
|
||||
!.env.example
|
||||
.codex
|
||||
8
.idea/.gitignore
generated
vendored
8
.idea/.gitignore
generated
vendored
@@ -1,8 +0,0 @@
|
||||
# Default ignored files
|
||||
/shelf/
|
||||
/workspace.xml
|
||||
# Editor-based HTTP Client requests
|
||||
/httpRequests/
|
||||
# Datasource local storage ignored files
|
||||
/dataSources/
|
||||
/dataSources.local.xml
|
||||
65
.idea/codeStyles/Project.xml
generated
65
.idea/codeStyles/Project.xml
generated
@@ -1,65 +0,0 @@
|
||||
<component name="ProjectCodeStyleConfiguration">
|
||||
<code_scheme name="Project" version="173">
|
||||
<HTMLCodeStyleSettings>
|
||||
<option name="HTML_SPACE_INSIDE_EMPTY_TAG" value="true" />
|
||||
<option name="HTML_QUOTE_STYLE" value="Single" />
|
||||
<option name="HTML_ENFORCE_QUOTES" value="true" />
|
||||
</HTMLCodeStyleSettings>
|
||||
<JSCodeStyleSettings version="0">
|
||||
<option name="FORCE_SEMICOLON_STYLE" value="true" />
|
||||
<option name="SPACE_BEFORE_FUNCTION_LEFT_PARENTH" value="false" />
|
||||
<option name="USE_DOUBLE_QUOTES" value="false" />
|
||||
<option name="FORCE_QUOTE_STYlE" value="true" />
|
||||
<option name="ENFORCE_TRAILING_COMMA" value="Remove" />
|
||||
<option name="SPACES_WITHIN_OBJECT_LITERAL_BRACES" value="true" />
|
||||
<option name="SPACES_WITHIN_IMPORTS" value="true" />
|
||||
</JSCodeStyleSettings>
|
||||
<TypeScriptCodeStyleSettings version="0">
|
||||
<option name="FORCE_SEMICOLON_STYLE" value="true" />
|
||||
<option name="SPACE_BEFORE_FUNCTION_LEFT_PARENTH" value="false" />
|
||||
<option name="USE_DOUBLE_QUOTES" value="false" />
|
||||
<option name="FORCE_QUOTE_STYlE" value="true" />
|
||||
<option name="ENFORCE_TRAILING_COMMA" value="Remove" />
|
||||
<option name="SPACES_WITHIN_OBJECT_LITERAL_BRACES" value="true" />
|
||||
<option name="SPACES_WITHIN_IMPORTS" value="true" />
|
||||
</TypeScriptCodeStyleSettings>
|
||||
<VueCodeStyleSettings>
|
||||
<option name="INTERPOLATION_NEW_LINE_AFTER_START_DELIMITER" value="false" />
|
||||
<option name="INTERPOLATION_NEW_LINE_BEFORE_END_DELIMITER" value="false" />
|
||||
</VueCodeStyleSettings>
|
||||
<codeStyleSettings language="HTML">
|
||||
<option name="SOFT_MARGINS" value="80" />
|
||||
<indentOptions>
|
||||
<option name="INDENT_SIZE" value="2" />
|
||||
<option name="CONTINUATION_INDENT_SIZE" value="2" />
|
||||
<option name="TAB_SIZE" value="2" />
|
||||
<option name="USE_TAB_CHARACTER" value="true" />
|
||||
</indentOptions>
|
||||
</codeStyleSettings>
|
||||
<codeStyleSettings language="JavaScript">
|
||||
<option name="SOFT_MARGINS" value="80" />
|
||||
<indentOptions>
|
||||
<option name="INDENT_SIZE" value="2" />
|
||||
<option name="CONTINUATION_INDENT_SIZE" value="2" />
|
||||
<option name="TAB_SIZE" value="2" />
|
||||
<option name="USE_TAB_CHARACTER" value="true" />
|
||||
</indentOptions>
|
||||
</codeStyleSettings>
|
||||
<codeStyleSettings language="TypeScript">
|
||||
<option name="SOFT_MARGINS" value="80" />
|
||||
<indentOptions>
|
||||
<option name="INDENT_SIZE" value="2" />
|
||||
<option name="CONTINUATION_INDENT_SIZE" value="2" />
|
||||
<option name="TAB_SIZE" value="2" />
|
||||
<option name="USE_TAB_CHARACTER" value="true" />
|
||||
</indentOptions>
|
||||
</codeStyleSettings>
|
||||
<codeStyleSettings language="Vue">
|
||||
<option name="SOFT_MARGINS" value="80" />
|
||||
<indentOptions>
|
||||
<option name="CONTINUATION_INDENT_SIZE" value="2" />
|
||||
<option name="USE_TAB_CHARACTER" value="true" />
|
||||
</indentOptions>
|
||||
</codeStyleSettings>
|
||||
</code_scheme>
|
||||
</component>
|
||||
5
.idea/codeStyles/codeStyleConfig.xml
generated
5
.idea/codeStyles/codeStyleConfig.xml
generated
@@ -1,5 +0,0 @@
|
||||
<component name="ProjectCodeStyleConfiguration">
|
||||
<state>
|
||||
<option name="USE_PER_PROJECT_SETTINGS" value="true" />
|
||||
</state>
|
||||
</component>
|
||||
7
.idea/discord.xml
generated
7
.idea/discord.xml
generated
@@ -1,7 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="DiscordProjectSettings">
|
||||
<option name="show" value="PROJECT_FILES" />
|
||||
<option name="description" value="" />
|
||||
</component>
|
||||
</project>
|
||||
10
.idea/inspectionProfiles/Project_Default.xml
generated
10
.idea/inspectionProfiles/Project_Default.xml
generated
@@ -1,10 +0,0 @@
|
||||
<component name="InspectionProjectProfileManager">
|
||||
<profile version="1.0">
|
||||
<option name="myName" value="Project Default" />
|
||||
<inspection_tool class="SpellCheckingInspection" enabled="false" level="TYPO" enabled_by_default="false">
|
||||
<option name="processCode" value="true" />
|
||||
<option name="processLiterals" value="true" />
|
||||
<option name="processComments" value="true" />
|
||||
</inspection_tool>
|
||||
</profile>
|
||||
</component>
|
||||
6
.idea/misc.xml
generated
6
.idea/misc.xml
generated
@@ -1,6 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="ProjectRootManager">
|
||||
<output url="file://$PROJECT_DIR$/out" />
|
||||
</component>
|
||||
</project>
|
||||
8
.idea/modules.xml
generated
8
.idea/modules.xml
generated
@@ -1,8 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="ProjectModuleManager">
|
||||
<modules>
|
||||
<module fileurl="file://$PROJECT_DIR$/.idea/vinci.iml" filepath="$PROJECT_DIR$/.idea/vinci.iml" />
|
||||
</modules>
|
||||
</component>
|
||||
</project>
|
||||
6
.idea/vcs.xml
generated
6
.idea/vcs.xml
generated
@@ -1,6 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="VcsDirectoryMappings">
|
||||
<mapping directory="" vcs="Git" />
|
||||
</component>
|
||||
</project>
|
||||
9
.idea/vinci.iml
generated
9
.idea/vinci.iml
generated
@@ -1,9 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<module type="JAVA_MODULE" version="4">
|
||||
<component name="NewModuleRootManager" inherit-compiler-output="true">
|
||||
<exclude-output />
|
||||
<content url="file://$MODULE_DIR$" />
|
||||
<orderEntry type="inheritedJdk" />
|
||||
<orderEntry type="sourceFolder" forTests="false" />
|
||||
</component>
|
||||
</module>
|
||||
@@ -1,5 +1,8 @@
|
||||
{
|
||||
"tabWidth": 2,
|
||||
"useTabs": true,
|
||||
"singleQuote": true
|
||||
"useTabs": false,
|
||||
"printWidth": 100,
|
||||
"tabWidth": 2,
|
||||
"singleQuote": true,
|
||||
"trailingComma": "es5",
|
||||
"semi": true
|
||||
}
|
||||
6
.vscode/settings.json
vendored
6
.vscode/settings.json
vendored
@@ -1,3 +1,7 @@
|
||||
{
|
||||
"dotenv.enableAutocloaking": false
|
||||
"dotenv.enableAutocloaking": false,
|
||||
"editor.tabSize": 2,
|
||||
"editor.detectIndentation": false,
|
||||
"editor.insertSpaces": true,
|
||||
"editor.rulers": [100]
|
||||
}
|
||||
51
Dockerfile
51
Dockerfile
@@ -1,32 +1,39 @@
|
||||
FROM node:lts
|
||||
|
||||
# Build stage
|
||||
FROM node:lts-alpine AS build
|
||||
|
||||
FROM oven/bun:alpine AS base
|
||||
WORKDIR /app
|
||||
RUN bun add -g @sern/cli
|
||||
|
||||
RUN apk add --no-cache --virtual .gyp python3 make g++
|
||||
|
||||
COPY package.json yarn.lock ./
|
||||
RUN yarn
|
||||
# Install dependencies
|
||||
FROM base AS deps
|
||||
COPY package.json bun.lock ./
|
||||
RUN bun install --frozen-lockfile --ignore-scripts
|
||||
|
||||
# Build the application
|
||||
FROM base AS build
|
||||
COPY --from=deps /app/node_modules ./node_modules
|
||||
COPY . .
|
||||
RUN yarn build
|
||||
RUN yarn cache clean
|
||||
|
||||
# Final stage
|
||||
FROM node:lts-alpine AS final
|
||||
RUN bun prisma generate
|
||||
RUN bun run build
|
||||
|
||||
# Production image
|
||||
FROM base AS runner
|
||||
WORKDIR /app
|
||||
|
||||
COPY --from=build /app/dist ./dist
|
||||
COPY --from=build /app/schemas ./schemas
|
||||
COPY --from=build /app/util ./
|
||||
COPY --from=build /app/images ./images
|
||||
COPY --from=build /app/node_modules ./node_modules
|
||||
COPY --from=build /app/package.json ./package.json
|
||||
RUN apk add --no-cache ffmpeg msttcorefonts-installer fontconfig && \
|
||||
ENV NODE_ENV=production
|
||||
|
||||
# Install system dependencies
|
||||
RUN apk add --no-cache ffmpeg fontconfig ttf-opensans msttcorefonts-installer && \
|
||||
update-ms-fonts && \
|
||||
fc-cache -f
|
||||
|
||||
CMD ["node", "dist/index.js"]
|
||||
RUN mkdir -p ./src/utils/db && \
|
||||
wget -O ./src/utils/db/dict.db https://github.com/SrIzan10/vinci/releases/download/dict-1/dict.db
|
||||
|
||||
COPY --from=build /app/node_modules ./node_modules
|
||||
COPY --from=build /app/dist ./dist
|
||||
COPY --from=build /app/assets ./assets
|
||||
COPY --from=build /app/images ./images
|
||||
COPY --from=build /app/.sern ./.sern
|
||||
COPY --from=build /app/package.json ./package.json
|
||||
COPY --from=build /app/prisma ./prisma
|
||||
|
||||
CMD ["sh", "-c", "bun run db:migrate && bun dist/index.js"]
|
||||
|
||||
67
README.md
67
README.md
@@ -1,35 +1,46 @@
|
||||
vinci bot
|
||||
# vinci v2
|
||||
|
||||
# little shoutout
|
||||
this discord bot has been made with [sern handler](https://sern.dev) and MAN I LOVE THIS HANDLER.
|
||||
Vinci v2 is a rewrite of my first JS project, a discord bot for [my favorite book series](https://maraturing.com) server. It aims to improve the code quality of the primary codebase, full of bugs and spaghetti code.
|
||||
|
||||
the maintainers helped me out from day one of the bot (and also teached me a lotta js along the way)
|
||||
It is written, as always, under the [sern](https://sern.dev) framework.
|
||||
|
||||
so tysm for everything, and I hope I can continue making new bots with this <3
|
||||
It is 85% done, with hardest commands implemented.
|
||||
|
||||
(also, fellow programmer, consider using it please)
|
||||
This is a bot submission for [Converge](https://converge.hackclub.com) and [Summer of Making](https://summer.hackclub.com).
|
||||
|
||||
# badges yes sir
|
||||
[](https://www.codefactor.io/repository/github/srizan10/vinci) [](https://wakatime.com/badge/user/4ad16edf-eadc-48d9-b010-26f275fe0be6/project/120bd895-55e3-42fe-894b-bd974f6f7312)
|
||||
## New features
|
||||
- More fun games
|
||||
- Modern typescript and discord.js
|
||||
- SQLite + Prisma instead of MongoDB + Mongoose
|
||||
- Less API queries and more performance by using local datasets (like the Spanish dictionary)
|
||||
|
||||
# warning and stuff
|
||||
# Available commands
|
||||
- `/rolemenu` - Role selection menu (owner only)
|
||||
- `/sugerencias` - Send a suggestion to the channel with upvote/downvote buttons
|
||||
- `/mcform` - Submit a form to join a Minecraft server
|
||||
- `/ip` - Get information about the Minecraft server IP
|
||||
- `/acortar` - Shorten a URL
|
||||
- `/wikipedia` - Search Wikipedia (Spanish/English)
|
||||
- `/8ball` - Ask the magic 8-ball a question
|
||||
- `/a` - Autogenerated "A" text with user autocomplete
|
||||
- `/chiste` - Get a random joke from a local dataset
|
||||
- `/google` - The most useless Google search command
|
||||
- `/hangman` - Play a game of hangman
|
||||
- `/makesweet` - Generate a heart locket image
|
||||
- `/megamind` - Generate a Megamind meme with custom text
|
||||
- `/palabra` - Returns a random Spanish word. That is it.
|
||||
- `/rps` - Play rock paper scissors against someone
|
||||
### Other stuff
|
||||
- Bonzify - Text-to-speech with Bonzi Buddy voice
|
||||
- Cursivify - Italicize message text
|
||||
- Image classification - Classify images using Cloudflare AI
|
||||
- AI chat - Chat with AI on a channel
|
||||
|
||||
this bot has been entirely coded by me, with absolutely no youtube tutorials.
|
||||
the code is here for transparency purposes and it's not made to be hosted by third parties.
|
||||
|
||||
# heres a roadmap (REALLY OUTDATED)
|
||||
|
||||
- ~~form to apply for the minecraft server~~ DONE!
|
||||
- ~~moderation commands~~ DONE!
|
||||
- ~~welcome to users~~ DONE!
|
||||
- modmail
|
||||
- ~~socials notification system~~ DONE!
|
||||
- chatbot using IBM's AI (thanks @gosevil for the idea)
|
||||
- ~~joke command~~
|
||||
|
||||
<!--<img src="https://srizan.s-ul.eu/RddzT2f9">-->
|
||||
|
||||
<img src="https://cdn.discordapp.com/attachments/928230817673641995/1036390945945559140/makesweet-hbt4h3.gif">
|
||||
by @Oliverlg8
|
||||
|
||||
10 stars! tysm!
|
||||
## Development setup
|
||||
1. Clone the repository
|
||||
2. Run `bun install`
|
||||
3. Install the sern cli: `npm install -g @sern/cli`
|
||||
4. Create a copy of `.env.example` and rename it to `.env`
|
||||
5. Fill in the file
|
||||
6. Run `bunx prisma migrate dev` to set up the database
|
||||
7. Run `bun dev`
|
||||
55
TODO.md
Normal file
55
TODO.md
Normal file
@@ -0,0 +1,55 @@
|
||||
# Slash Commands
|
||||
|
||||
## Fun Commands
|
||||
- [ ] /animal - Animal pictures with voting system (cat, dog, capybara, fox, raccoon)
|
||||
- [x] /chiste - Joke command fetching from API
|
||||
- [x] /rps - Rock Paper Scissors game
|
||||
- [x] /8ball - Magic 8-ball responses
|
||||
- [x] /megamind - Megamind meme generator with canvas
|
||||
- [x] /makesweet - Heart locket image generator
|
||||
- [x] /a - Custom command with user autocomplete
|
||||
|
||||
## Miscellaneous Commands
|
||||
- [x] /rolemenu - Role selection menu (owner only)
|
||||
- [ ] /creditos - Bot credits and acknowledgments
|
||||
- [x] ~~/infinitecraft - InfiniteCraft recipe solver~~
|
||||
- [ ] /letra - Song lyrics search via Genius API
|
||||
- [x] /google - Google search results
|
||||
- [x] /sugerencias - Suggestion system with upvote/downvote
|
||||
- [x] /wikipedia - Wikipedia search (Spanish/English)
|
||||
- [ ] /faq - FAQ system with Minecraft questions
|
||||
- [ ] ~~/afk - AFK status management~~
|
||||
- [x] /acortar - URL shortener
|
||||
|
||||
## Minecraft Commands
|
||||
- [x] /ip - Minecraft server IP information
|
||||
- [x] /mcform - Minecraft form submission
|
||||
|
||||
# Button Handlers
|
||||
- [x] suggestions-yes - Upvote button handler
|
||||
- [x] suggestions-no - Downvote button handler
|
||||
- [x] suggestions-yes-who - Show upvoters
|
||||
- [x] suggestions-no-who - Show downvoters
|
||||
|
||||
# Context Menu Commands
|
||||
- [x] bonzify - Text-to-speech with Bonzi Buddy voice
|
||||
- [x] cursivify - Italicize message text
|
||||
- [x] image-classification - Cloudflare AI image classification
|
||||
|
||||
# Message driven functions
|
||||
- [x] AI chat
|
||||
|
||||
# Utility Systems to Rewrite
|
||||
- [x] Resolver - Role/user resolution utility
|
||||
- [x] Wikipedia utility - Wikipedia search helper
|
||||
|
||||
# Background Services
|
||||
- [x] ~YouTube notifications system~ using rss instead
|
||||
- [x] Birthday checker service
|
||||
- [x] Activity status rotation
|
||||
|
||||
# Database
|
||||
- [x] Migration to sqlite
|
||||
|
||||
# Other
|
||||
- [ ] Figure out fonts
|
||||
1
assets/chistes.json
Normal file
1
assets/chistes.json
Normal file
File diff suppressed because one or more lines are too long
1059783
assets/icRecipes.json
Normal file
1059783
assets/icRecipes.json
Normal file
File diff suppressed because it is too large
Load Diff
584
bun.lock
Normal file
584
bun.lock
Normal file
@@ -0,0 +1,584 @@
|
||||
{
|
||||
"lockfileVersion": 1,
|
||||
"configVersion": 0,
|
||||
"workspaces": {
|
||||
"": {
|
||||
"name": "ts-example",
|
||||
"dependencies": {
|
||||
"@napi-rs/canvas": "^0.1.72",
|
||||
"@prisma/client": "^6.10.1",
|
||||
"@sern/handler": "^4.2.4",
|
||||
"@sern/publisher": "1.1.2",
|
||||
"discord.js": "^14.21.0",
|
||||
"dotenv": "^16.3.1",
|
||||
"execa": "^9.6.0",
|
||||
"mongodb": "^6.17.0",
|
||||
"node-html-parser": "^7.0.1",
|
||||
"openai": "^5.10.2",
|
||||
"rockpaperscissors-checker": "^1.2.0",
|
||||
"sharp": "^0.34.2",
|
||||
},
|
||||
"devDependencies": {
|
||||
"@sern/cli": "^1.4.0",
|
||||
"@types/bun": "^1.2.18",
|
||||
"@types/mongodb": "^4.0.7",
|
||||
"@types/node": "^17.0.25",
|
||||
"prisma": "^6.10.1",
|
||||
"typescript": "^5.0",
|
||||
},
|
||||
},
|
||||
},
|
||||
"packages": {
|
||||
"@discordjs/builders": ["@discordjs/builders@1.11.2", "", { "dependencies": { "@discordjs/formatters": "^0.6.1", "@discordjs/util": "^1.1.1", "@sapphire/shapeshift": "^4.0.0", "discord-api-types": "^0.38.1", "fast-deep-equal": "^3.1.3", "ts-mixer": "^6.0.4", "tslib": "^2.6.3" } }, "sha512-F1WTABdd8/R9D1icJzajC4IuLyyS8f3rTOz66JsSI3pKvpCAtsMBweu8cyNYsIyvcrKAVn9EPK+Psoymq+XC0A=="],
|
||||
|
||||
"@discordjs/collection": ["@discordjs/collection@1.5.3", "", {}, "sha512-SVb428OMd3WO1paV3rm6tSjM4wC+Kecaa1EUGX7vc6/fddvw/6lg90z4QtCqm21zvVe92vMMDt9+DkIvjXImQQ=="],
|
||||
|
||||
"@discordjs/formatters": ["@discordjs/formatters@0.6.1", "", { "dependencies": { "discord-api-types": "^0.38.1" } }, "sha512-5cnX+tASiPCqCWtFcFslxBVUaCetB0thvM/JyavhbXInP1HJIEU+Qv/zMrnuwSsX3yWH2lVXNJZeDK3EiP4HHg=="],
|
||||
|
||||
"@discordjs/rest": ["@discordjs/rest@2.5.1", "", { "dependencies": { "@discordjs/collection": "^2.1.1", "@discordjs/util": "^1.1.1", "@sapphire/async-queue": "^1.5.3", "@sapphire/snowflake": "^3.5.3", "@vladfrangu/async_event_emitter": "^2.4.6", "discord-api-types": "^0.38.1", "magic-bytes.js": "^1.10.0", "tslib": "^2.6.3", "undici": "6.21.3" } }, "sha512-Tg9840IneBcbrAjcGaQzHUJWFNq1MMWZjTdjJ0WS/89IffaNKc++iOvffucPxQTF/gviO9+9r8kEPea1X5J2Dw=="],
|
||||
|
||||
"@discordjs/util": ["@discordjs/util@1.1.1", "", {}, "sha512-eddz6UnOBEB1oITPinyrB2Pttej49M9FZQY8NxgEvc3tq6ZICZ19m70RsmzRdDHk80O9NoYN/25AqJl8vPVf/g=="],
|
||||
|
||||
"@discordjs/ws": ["@discordjs/ws@1.2.3", "", { "dependencies": { "@discordjs/collection": "^2.1.0", "@discordjs/rest": "^2.5.1", "@discordjs/util": "^1.1.0", "@sapphire/async-queue": "^1.5.2", "@types/ws": "^8.5.10", "@vladfrangu/async_event_emitter": "^2.2.4", "discord-api-types": "^0.38.1", "tslib": "^2.6.2", "ws": "^8.17.0" } }, "sha512-wPlQDxEmlDg5IxhJPuxXr3Vy9AjYq5xCvFWGJyD7w7Np8ZGu+Mc+97LCoEc/+AYCo2IDpKioiH0/c/mj5ZR9Uw=="],
|
||||
|
||||
"@emnapi/runtime": ["@emnapi/runtime@1.4.3", "", { "dependencies": { "tslib": "^2.4.0" } }, "sha512-pBPWdu6MLKROBX05wSNKcNb++m5Er+KQ9QkB+WVM+pW2Kx9hoSrVTnu3BdkI5eBLZoKu/J6mW/B6i6bJB2ytXQ=="],
|
||||
|
||||
"@esbuild-kit/cjs-loader": ["@esbuild-kit/cjs-loader@2.4.4", "", { "dependencies": { "@esbuild-kit/core-utils": "^3.2.3", "get-tsconfig": "^4.7.0" } }, "sha512-NfsJX4PdzhwSkfJukczyUiZGc7zNNWZcEAyqeISpDnn0PTfzMJR1aR8xAIPskBejIxBJbIgCCMzbaYa9SXepIg=="],
|
||||
|
||||
"@esbuild-kit/core-utils": ["@esbuild-kit/core-utils@3.3.2", "", { "dependencies": { "esbuild": "~0.18.20", "source-map-support": "^0.5.21" } }, "sha512-sPRAnw9CdSsRmEtnsl2WXWdyquogVpB3yZ3dgwJfe8zrOzTsV7cJvmwrKVa+0ma5BoiGJ+BoqkMvawbayKUsqQ=="],
|
||||
|
||||
"@esbuild-kit/esm-loader": ["@esbuild-kit/esm-loader@2.6.5", "", { "dependencies": { "@esbuild-kit/core-utils": "^3.3.2", "get-tsconfig": "^4.7.0" } }, "sha512-FxEMIkJKnodyA1OaCUoEvbYRkoZlLZ4d/eXFu9Fh8CbBBgP5EmZxrfTRyN0qpXZ4vOvqnE5YdRdcrmUUXuU+dA=="],
|
||||
|
||||
"@esbuild/aix-ppc64": ["@esbuild/aix-ppc64@0.19.12", "", { "os": "aix", "cpu": "ppc64" }, "sha512-bmoCYyWdEL3wDQIVbcyzRyeKLgk2WtWLTWz1ZIAZF/EGbNOwSA6ew3PftJ1PqMiOOGu0OyFMzG53L0zqIpPeNA=="],
|
||||
|
||||
"@esbuild/android-arm": ["@esbuild/android-arm@0.19.12", "", { "os": "android", "cpu": "arm" }, "sha512-qg/Lj1mu3CdQlDEEiWrlC4eaPZ1KztwGJ9B6J+/6G+/4ewxJg7gqj8eVYWvao1bXrqGiW2rsBZFSX3q2lcW05w=="],
|
||||
|
||||
"@esbuild/android-arm64": ["@esbuild/android-arm64@0.19.12", "", { "os": "android", "cpu": "arm64" }, "sha512-P0UVNGIienjZv3f5zq0DP3Nt2IE/3plFzuaS96vihvD0Hd6H/q4WXUGpCxD/E8YrSXfNyRPbpTq+T8ZQioSuPA=="],
|
||||
|
||||
"@esbuild/android-x64": ["@esbuild/android-x64@0.19.12", "", { "os": "android", "cpu": "x64" }, "sha512-3k7ZoUW6Q6YqhdhIaq/WZ7HwBpnFBlW905Fa4s4qWJyiNOgT1dOqDiVAQFwBH7gBRZr17gLrlFCRzF6jFh7Kew=="],
|
||||
|
||||
"@esbuild/darwin-arm64": ["@esbuild/darwin-arm64@0.19.12", "", { "os": "darwin", "cpu": "arm64" }, "sha512-B6IeSgZgtEzGC42jsI+YYu9Z3HKRxp8ZT3cqhvliEHovq8HSX2YX8lNocDn79gCKJXOSaEot9MVYky7AKjCs8g=="],
|
||||
|
||||
"@esbuild/darwin-x64": ["@esbuild/darwin-x64@0.19.12", "", { "os": "darwin", "cpu": "x64" }, "sha512-hKoVkKzFiToTgn+41qGhsUJXFlIjxI/jSYeZf3ugemDYZldIXIxhvwN6erJGlX4t5h417iFuheZ7l+YVn05N3A=="],
|
||||
|
||||
"@esbuild/freebsd-arm64": ["@esbuild/freebsd-arm64@0.19.12", "", { "os": "freebsd", "cpu": "arm64" }, "sha512-4aRvFIXmwAcDBw9AueDQ2YnGmz5L6obe5kmPT8Vd+/+x/JMVKCgdcRwH6APrbpNXsPz+K653Qg8HB/oXvXVukA=="],
|
||||
|
||||
"@esbuild/freebsd-x64": ["@esbuild/freebsd-x64@0.19.12", "", { "os": "freebsd", "cpu": "x64" }, "sha512-EYoXZ4d8xtBoVN7CEwWY2IN4ho76xjYXqSXMNccFSx2lgqOG/1TBPW0yPx1bJZk94qu3tX0fycJeeQsKovA8gg=="],
|
||||
|
||||
"@esbuild/linux-arm": ["@esbuild/linux-arm@0.19.12", "", { "os": "linux", "cpu": "arm" }, "sha512-J5jPms//KhSNv+LO1S1TX1UWp1ucM6N6XuL6ITdKWElCu8wXP72l9MM0zDTzzeikVyqFE6U8YAV9/tFyj0ti+w=="],
|
||||
|
||||
"@esbuild/linux-arm64": ["@esbuild/linux-arm64@0.19.12", "", { "os": "linux", "cpu": "arm64" }, "sha512-EoTjyYyLuVPfdPLsGVVVC8a0p1BFFvtpQDB/YLEhaXyf/5bczaGeN15QkR+O4S5LeJ92Tqotve7i1jn35qwvdA=="],
|
||||
|
||||
"@esbuild/linux-ia32": ["@esbuild/linux-ia32@0.19.12", "", { "os": "linux", "cpu": "ia32" }, "sha512-Thsa42rrP1+UIGaWz47uydHSBOgTUnwBwNq59khgIwktK6x60Hivfbux9iNR0eHCHzOLjLMLfUMLCypBkZXMHA=="],
|
||||
|
||||
"@esbuild/linux-loong64": ["@esbuild/linux-loong64@0.19.12", "", { "os": "linux", "cpu": "none" }, "sha512-LiXdXA0s3IqRRjm6rV6XaWATScKAXjI4R4LoDlvO7+yQqFdlr1Bax62sRwkVvRIrwXxvtYEHHI4dm50jAXkuAA=="],
|
||||
|
||||
"@esbuild/linux-mips64el": ["@esbuild/linux-mips64el@0.19.12", "", { "os": "linux", "cpu": "none" }, "sha512-fEnAuj5VGTanfJ07ff0gOA6IPsvrVHLVb6Lyd1g2/ed67oU1eFzL0r9WL7ZzscD+/N6i3dWumGE1Un4f7Amf+w=="],
|
||||
|
||||
"@esbuild/linux-ppc64": ["@esbuild/linux-ppc64@0.19.12", "", { "os": "linux", "cpu": "ppc64" }, "sha512-nYJA2/QPimDQOh1rKWedNOe3Gfc8PabU7HT3iXWtNUbRzXS9+vgB0Fjaqr//XNbd82mCxHzik2qotuI89cfixg=="],
|
||||
|
||||
"@esbuild/linux-riscv64": ["@esbuild/linux-riscv64@0.19.12", "", { "os": "linux", "cpu": "none" }, "sha512-2MueBrlPQCw5dVJJpQdUYgeqIzDQgw3QtiAHUC4RBz9FXPrskyyU3VI1hw7C0BSKB9OduwSJ79FTCqtGMWqJHg=="],
|
||||
|
||||
"@esbuild/linux-s390x": ["@esbuild/linux-s390x@0.19.12", "", { "os": "linux", "cpu": "s390x" }, "sha512-+Pil1Nv3Umes4m3AZKqA2anfhJiVmNCYkPchwFJNEJN5QxmTs1uzyy4TvmDrCRNT2ApwSari7ZIgrPeUx4UZDg=="],
|
||||
|
||||
"@esbuild/linux-x64": ["@esbuild/linux-x64@0.19.12", "", { "os": "linux", "cpu": "x64" }, "sha512-B71g1QpxfwBvNrfyJdVDexenDIt1CiDN1TIXLbhOw0KhJzE78KIFGX6OJ9MrtC0oOqMWf+0xop4qEU8JrJTwCg=="],
|
||||
|
||||
"@esbuild/netbsd-x64": ["@esbuild/netbsd-x64@0.19.12", "", { "os": "none", "cpu": "x64" }, "sha512-3ltjQ7n1owJgFbuC61Oj++XhtzmymoCihNFgT84UAmJnxJfm4sYCiSLTXZtE00VWYpPMYc+ZQmB6xbSdVh0JWA=="],
|
||||
|
||||
"@esbuild/openbsd-x64": ["@esbuild/openbsd-x64@0.19.12", "", { "os": "openbsd", "cpu": "x64" }, "sha512-RbrfTB9SWsr0kWmb9srfF+L933uMDdu9BIzdA7os2t0TXhCRjrQyCeOt6wVxr79CKD4c+p+YhCj31HBkYcXebw=="],
|
||||
|
||||
"@esbuild/sunos-x64": ["@esbuild/sunos-x64@0.19.12", "", { "os": "sunos", "cpu": "x64" }, "sha512-HKjJwRrW8uWtCQnQOz9qcU3mUZhTUQvi56Q8DPTLLB+DawoiQdjsYq+j+D3s9I8VFtDr+F9CjgXKKC4ss89IeA=="],
|
||||
|
||||
"@esbuild/win32-arm64": ["@esbuild/win32-arm64@0.19.12", "", { "os": "win32", "cpu": "arm64" }, "sha512-URgtR1dJnmGvX864pn1B2YUYNzjmXkuJOIqG2HdU62MVS4EHpU2946OZoTMnRUHklGtJdJZ33QfzdjGACXhn1A=="],
|
||||
|
||||
"@esbuild/win32-ia32": ["@esbuild/win32-ia32@0.19.12", "", { "os": "win32", "cpu": "ia32" }, "sha512-+ZOE6pUkMOJfmxmBZElNOx72NKpIa/HFOMGzu8fqzQJ5kgf6aTGrcJaFsNiVMH4JKpMipyK+7k0n2UXN7a8YKQ=="],
|
||||
|
||||
"@esbuild/win32-x64": ["@esbuild/win32-x64@0.19.12", "", { "os": "win32", "cpu": "x64" }, "sha512-T1QyPSDCyMXaO3pzBkF96E8xMkiRYbUEZADd29SyPGabqxMViNoii+NcK7eWJAEoU6RZyEm5lVSIjTmcdoB9HA=="],
|
||||
|
||||
"@img/sharp-darwin-arm64": ["@img/sharp-darwin-arm64@0.34.2", "", { "optionalDependencies": { "@img/sharp-libvips-darwin-arm64": "1.1.0" }, "os": "darwin", "cpu": "arm64" }, "sha512-OfXHZPppddivUJnqyKoi5YVeHRkkNE2zUFT2gbpKxp/JZCFYEYubnMg+gOp6lWfasPrTS+KPosKqdI+ELYVDtg=="],
|
||||
|
||||
"@img/sharp-darwin-x64": ["@img/sharp-darwin-x64@0.34.2", "", { "optionalDependencies": { "@img/sharp-libvips-darwin-x64": "1.1.0" }, "os": "darwin", "cpu": "x64" }, "sha512-dYvWqmjU9VxqXmjEtjmvHnGqF8GrVjM2Epj9rJ6BUIXvk8slvNDJbhGFvIoXzkDhrJC2jUxNLz/GUjjvSzfw+g=="],
|
||||
|
||||
"@img/sharp-libvips-darwin-arm64": ["@img/sharp-libvips-darwin-arm64@1.1.0", "", { "os": "darwin", "cpu": "arm64" }, "sha512-HZ/JUmPwrJSoM4DIQPv/BfNh9yrOA8tlBbqbLz4JZ5uew2+o22Ik+tHQJcih7QJuSa0zo5coHTfD5J8inqj9DA=="],
|
||||
|
||||
"@img/sharp-libvips-darwin-x64": ["@img/sharp-libvips-darwin-x64@1.1.0", "", { "os": "darwin", "cpu": "x64" }, "sha512-Xzc2ToEmHN+hfvsl9wja0RlnXEgpKNmftriQp6XzY/RaSfwD9th+MSh0WQKzUreLKKINb3afirxW7A0fz2YWuQ=="],
|
||||
|
||||
"@img/sharp-libvips-linux-arm": ["@img/sharp-libvips-linux-arm@1.1.0", "", { "os": "linux", "cpu": "arm" }, "sha512-s8BAd0lwUIvYCJyRdFqvsj+BJIpDBSxs6ivrOPm/R7piTs5UIwY5OjXrP2bqXC9/moGsyRa37eYWYCOGVXxVrA=="],
|
||||
|
||||
"@img/sharp-libvips-linux-arm64": ["@img/sharp-libvips-linux-arm64@1.1.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-IVfGJa7gjChDET1dK9SekxFFdflarnUB8PwW8aGwEoF3oAsSDuNUTYS+SKDOyOJxQyDC1aPFMuRYLoDInyV9Ew=="],
|
||||
|
||||
"@img/sharp-libvips-linux-ppc64": ["@img/sharp-libvips-linux-ppc64@1.1.0", "", { "os": "linux", "cpu": "ppc64" }, "sha512-tiXxFZFbhnkWE2LA8oQj7KYR+bWBkiV2nilRldT7bqoEZ4HiDOcePr9wVDAZPi/Id5fT1oY9iGnDq20cwUz8lQ=="],
|
||||
|
||||
"@img/sharp-libvips-linux-s390x": ["@img/sharp-libvips-linux-s390x@1.1.0", "", { "os": "linux", "cpu": "s390x" }, "sha512-xukSwvhguw7COyzvmjydRb3x/09+21HykyapcZchiCUkTThEQEOMtBj9UhkaBRLuBrgLFzQ2wbxdeCCJW/jgJA=="],
|
||||
|
||||
"@img/sharp-libvips-linux-x64": ["@img/sharp-libvips-linux-x64@1.1.0", "", { "os": "linux", "cpu": "x64" }, "sha512-yRj2+reB8iMg9W5sULM3S74jVS7zqSzHG3Ol/twnAAkAhnGQnpjj6e4ayUz7V+FpKypwgs82xbRdYtchTTUB+Q=="],
|
||||
|
||||
"@img/sharp-libvips-linuxmusl-arm64": ["@img/sharp-libvips-linuxmusl-arm64@1.1.0", "", { "os": "linux", "cpu": "arm64" }, "sha512-jYZdG+whg0MDK+q2COKbYidaqW/WTz0cc1E+tMAusiDygrM4ypmSCjOJPmFTvHHJ8j/6cAGyeDWZOsK06tP33w=="],
|
||||
|
||||
"@img/sharp-libvips-linuxmusl-x64": ["@img/sharp-libvips-linuxmusl-x64@1.1.0", "", { "os": "linux", "cpu": "x64" }, "sha512-wK7SBdwrAiycjXdkPnGCPLjYb9lD4l6Ze2gSdAGVZrEL05AOUJESWU2lhlC+Ffn5/G+VKuSm6zzbQSzFX/P65A=="],
|
||||
|
||||
"@img/sharp-linux-arm": ["@img/sharp-linux-arm@0.34.2", "", { "optionalDependencies": { "@img/sharp-libvips-linux-arm": "1.1.0" }, "os": "linux", "cpu": "arm" }, "sha512-0DZzkvuEOqQUP9mo2kjjKNok5AmnOr1jB2XYjkaoNRwpAYMDzRmAqUIa1nRi58S2WswqSfPOWLNOr0FDT3H5RQ=="],
|
||||
|
||||
"@img/sharp-linux-arm64": ["@img/sharp-linux-arm64@0.34.2", "", { "optionalDependencies": { "@img/sharp-libvips-linux-arm64": "1.1.0" }, "os": "linux", "cpu": "arm64" }, "sha512-D8n8wgWmPDakc83LORcfJepdOSN6MvWNzzz2ux0MnIbOqdieRZwVYY32zxVx+IFUT8er5KPcyU3XXsn+GzG/0Q=="],
|
||||
|
||||
"@img/sharp-linux-s390x": ["@img/sharp-linux-s390x@0.34.2", "", { "optionalDependencies": { "@img/sharp-libvips-linux-s390x": "1.1.0" }, "os": "linux", "cpu": "s390x" }, "sha512-EGZ1xwhBI7dNISwxjChqBGELCWMGDvmxZXKjQRuqMrakhO8QoMgqCrdjnAqJq/CScxfRn+Bb7suXBElKQpPDiw=="],
|
||||
|
||||
"@img/sharp-linux-x64": ["@img/sharp-linux-x64@0.34.2", "", { "optionalDependencies": { "@img/sharp-libvips-linux-x64": "1.1.0" }, "os": "linux", "cpu": "x64" }, "sha512-sD7J+h5nFLMMmOXYH4DD9UtSNBD05tWSSdWAcEyzqW8Cn5UxXvsHAxmxSesYUsTOBmUnjtxghKDl15EvfqLFbQ=="],
|
||||
|
||||
"@img/sharp-linuxmusl-arm64": ["@img/sharp-linuxmusl-arm64@0.34.2", "", { "optionalDependencies": { "@img/sharp-libvips-linuxmusl-arm64": "1.1.0" }, "os": "linux", "cpu": "arm64" }, "sha512-NEE2vQ6wcxYav1/A22OOxoSOGiKnNmDzCYFOZ949xFmrWZOVII1Bp3NqVVpvj+3UeHMFyN5eP/V5hzViQ5CZNA=="],
|
||||
|
||||
"@img/sharp-linuxmusl-x64": ["@img/sharp-linuxmusl-x64@0.34.2", "", { "optionalDependencies": { "@img/sharp-libvips-linuxmusl-x64": "1.1.0" }, "os": "linux", "cpu": "x64" }, "sha512-DOYMrDm5E6/8bm/yQLCWyuDJwUnlevR8xtF8bs+gjZ7cyUNYXiSf/E8Kp0Ss5xasIaXSHzb888V1BE4i1hFhAA=="],
|
||||
|
||||
"@img/sharp-wasm32": ["@img/sharp-wasm32@0.34.2", "", { "dependencies": { "@emnapi/runtime": "^1.4.3" }, "cpu": "none" }, "sha512-/VI4mdlJ9zkaq53MbIG6rZY+QRN3MLbR6usYlgITEzi4Rpx5S6LFKsycOQjkOGmqTNmkIdLjEvooFKwww6OpdQ=="],
|
||||
|
||||
"@img/sharp-win32-arm64": ["@img/sharp-win32-arm64@0.34.2", "", { "os": "win32", "cpu": "arm64" }, "sha512-cfP/r9FdS63VA5k0xiqaNaEoGxBg9k7uE+RQGzuK9fHt7jib4zAVVseR9LsE4gJcNWgT6APKMNnCcnyOtmSEUQ=="],
|
||||
|
||||
"@img/sharp-win32-ia32": ["@img/sharp-win32-ia32@0.34.2", "", { "os": "win32", "cpu": "ia32" }, "sha512-QLjGGvAbj0X/FXl8n1WbtQ6iVBpWU7JO94u/P2M4a8CFYsvQi4GW2mRy/JqkRx0qpBzaOdKJKw8uc930EX2AHw=="],
|
||||
|
||||
"@img/sharp-win32-x64": ["@img/sharp-win32-x64@0.34.2", "", { "os": "win32", "cpu": "x64" }, "sha512-aUdT6zEYtDKCaxkofmmJDJYGCf0+pJg3eU9/oBuqvEeoB9dKI6ZLc/1iLJCTuJQDO4ptntAlkUmHgGjyuobZbw=="],
|
||||
|
||||
"@isaacs/cliui": ["@isaacs/cliui@8.0.2", "", { "dependencies": { "string-width": "^5.1.2", "string-width-cjs": "npm:string-width@^4.2.0", "strip-ansi": "^7.0.1", "strip-ansi-cjs": "npm:strip-ansi@^6.0.1", "wrap-ansi": "^8.1.0", "wrap-ansi-cjs": "npm:wrap-ansi@^7.0.0" } }, "sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA=="],
|
||||
|
||||
"@mongodb-js/saslprep": ["@mongodb-js/saslprep@1.3.0", "", { "dependencies": { "sparse-bitfield": "^3.0.3" } }, "sha512-zlayKCsIjYb7/IdfqxorK5+xUMyi4vOKcFy10wKJYc63NSdKI8mNME+uJqfatkPmOSMMUiojrL58IePKBm3gvQ=="],
|
||||
|
||||
"@napi-rs/canvas": ["@napi-rs/canvas@0.1.72", "", { "optionalDependencies": { "@napi-rs/canvas-android-arm64": "0.1.72", "@napi-rs/canvas-darwin-arm64": "0.1.72", "@napi-rs/canvas-darwin-x64": "0.1.72", "@napi-rs/canvas-linux-arm-gnueabihf": "0.1.72", "@napi-rs/canvas-linux-arm64-gnu": "0.1.72", "@napi-rs/canvas-linux-arm64-musl": "0.1.72", "@napi-rs/canvas-linux-riscv64-gnu": "0.1.72", "@napi-rs/canvas-linux-x64-gnu": "0.1.72", "@napi-rs/canvas-linux-x64-musl": "0.1.72", "@napi-rs/canvas-win32-x64-msvc": "0.1.72" } }, "sha512-ypTJ/DXzsJbTU3o7qXFlWmZGgEbh42JWQl7v5/i+DJz/HURELcSnq9ler9e1ukqma70JzmCQcIseiE/Xs6sczw=="],
|
||||
|
||||
"@napi-rs/canvas-android-arm64": ["@napi-rs/canvas-android-arm64@0.1.72", "", { "os": "android", "cpu": "arm64" }, "sha512-OW99TDJEdfOhpJWQ7SXFsQi1BXd6UFuWM8AoQvJ0SQMHWY/iwuopmb1UqGV6Df9aM/SWxvCWBN/onjeCM8KVKQ=="],
|
||||
|
||||
"@napi-rs/canvas-darwin-arm64": ["@napi-rs/canvas-darwin-arm64@0.1.72", "", { "os": "darwin", "cpu": "arm64" }, "sha512-gB8Pn/4GdS+B6P4HYuNqPGx8iQJ16Go1D6e5hIxfUbA/efupVGZ7e3OMGWGCUgF0vgbEPEF31sPzhcad4mdR5g=="],
|
||||
|
||||
"@napi-rs/canvas-darwin-x64": ["@napi-rs/canvas-darwin-x64@0.1.72", "", { "os": "darwin", "cpu": "x64" }, "sha512-x1zKtWVSnf+yLETHdSDAFJ1w6bctS/V2NP0wskTTBKkC+c/AmI2Dl+ZMIW11gF6rilBibrIzBeXJKPzV0GMWGA=="],
|
||||
|
||||
"@napi-rs/canvas-linux-arm-gnueabihf": ["@napi-rs/canvas-linux-arm-gnueabihf@0.1.72", "", { "os": "linux", "cpu": "arm" }, "sha512-Ef6HMF+TBS+lqBNpcUj2D17ODJrbgevXaVPtr2nQFCao5IvoEhVMdmVwWk5YiI+GcgbAkg5AF3LiU47RoSY5yg=="],
|
||||
|
||||
"@napi-rs/canvas-linux-arm64-gnu": ["@napi-rs/canvas-linux-arm64-gnu@0.1.72", "", { "os": "linux", "cpu": "arm64" }, "sha512-i1tWu+Li1Z6G4t+ckT38JwuB/cAAREV6H8VD3dip2yTYU+qnLz6kG4i+whm+SEQb1e4vk3xA1lKnjYx3jlOy8g=="],
|
||||
|
||||
"@napi-rs/canvas-linux-arm64-musl": ["@napi-rs/canvas-linux-arm64-musl@0.1.72", "", { "os": "linux", "cpu": "arm64" }, "sha512-Mu+2hHZAT9SdrjiRtCxMD/Unac8vqVxF/p+Tvjb5sN1NZkLGu+l7WIfrug8aeX150OwrYgAvsR4mhrm0BZvLxg=="],
|
||||
|
||||
"@napi-rs/canvas-linux-riscv64-gnu": ["@napi-rs/canvas-linux-riscv64-gnu@0.1.72", "", { "os": "linux", "cpu": "none" }, "sha512-xBPG/ImL58I4Ep6VM+sCrpwl8rE/8e7Dt9U7zzggNvYHrWD13vIF3q5L2/N9VxdBMh1pee6dBC/VcaXLYccZNQ=="],
|
||||
|
||||
"@napi-rs/canvas-linux-x64-gnu": ["@napi-rs/canvas-linux-x64-gnu@0.1.72", "", { "os": "linux", "cpu": "x64" }, "sha512-jkC8L+QovHpzQrw+Jm1IUqxgLV5QB1hJ1cR8iYzxNRd0TOF7YfxLaIGxvd/ReRi9r48JT6PL7z2IGT7TqK8T4w=="],
|
||||
|
||||
"@napi-rs/canvas-linux-x64-musl": ["@napi-rs/canvas-linux-x64-musl@0.1.72", "", { "os": "linux", "cpu": "x64" }, "sha512-PwPdPmHgJYnTMUr8Gff80eRVdpGjwrxueIqw+7v4aeFxbQjmQ+paa2xaGedFtkvdS2Dn5z8a0mVlrlbSfec+1Q=="],
|
||||
|
||||
"@napi-rs/canvas-win32-x64-msvc": ["@napi-rs/canvas-win32-x64-msvc@0.1.72", "", { "os": "win32", "cpu": "x64" }, "sha512-hZhXJZZ/2ZjkAoOtyGUs3Mx6jA4o9ESbc5bk+NKYO6thZRvRNA7rqvT9WF9pZK0xcRK5EyWRymv8fCzqmSVEzg=="],
|
||||
|
||||
"@pkgjs/parseargs": ["@pkgjs/parseargs@0.11.0", "", {}, "sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg=="],
|
||||
|
||||
"@prisma/client": ["@prisma/client@6.10.1", "", { "peerDependencies": { "prisma": "*", "typescript": ">=5.1.0" }, "optionalPeers": ["prisma", "typescript"] }, "sha512-Re4pMlcUsQsUTAYMK7EJ4Bw2kg3WfZAAlr8GjORJaK4VOP6LxRQUQ1TuLnxcF42XqGkWQ36q5CQF1yVadANQ6w=="],
|
||||
|
||||
"@prisma/config": ["@prisma/config@6.10.1", "", { "dependencies": { "jiti": "2.4.2" } }, "sha512-kz4/bnqrOrzWo8KzYguN0cden4CzLJJ+2VSpKtF8utHS3l1JS0Lhv6BLwpOX6X9yNreTbZQZwewb+/BMPDCIYQ=="],
|
||||
|
||||
"@prisma/debug": ["@prisma/debug@6.10.1", "", {}, "sha512-k2YT53cWxv9OLjW4zSYTZ6Z7j0gPfCzcr2Mj99qsuvlxr8WAKSZ2NcSR0zLf/mP4oxnYG842IMj3utTgcd7CaA=="],
|
||||
|
||||
"@prisma/engines": ["@prisma/engines@6.10.1", "", { "dependencies": { "@prisma/debug": "6.10.1", "@prisma/engines-version": "6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c", "@prisma/fetch-engine": "6.10.1", "@prisma/get-platform": "6.10.1" } }, "sha512-Q07P5rS2iPwk2IQr/rUQJ42tHjpPyFcbiH7PXZlV81Ryr9NYIgdxcUrwgVOWVm5T7ap02C0dNd1dpnNcSWig8A=="],
|
||||
|
||||
"@prisma/engines-version": ["@prisma/engines-version@6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c", "", {}, "sha512-ZJFTsEqapiTYVzXya6TUKYDFnSWCNegfUiG5ik9fleQva5Sk3DNyyUi7X1+0ZxWFHwHDr6BZV5Vm+iwP+LlciA=="],
|
||||
|
||||
"@prisma/fetch-engine": ["@prisma/fetch-engine@6.10.1", "", { "dependencies": { "@prisma/debug": "6.10.1", "@prisma/engines-version": "6.10.1-1.9b628578b3b7cae625e8c927178f15a170e74a9c", "@prisma/get-platform": "6.10.1" } }, "sha512-clmbG/Jgmrc/n6Y77QcBmAUlq9LrwI9Dbgy4pq5jeEARBpRCWJDJ7PWW1P8p0LfFU0i5fsyO7FqRzRB8mkdS4g=="],
|
||||
|
||||
"@prisma/get-platform": ["@prisma/get-platform@6.10.1", "", { "dependencies": { "@prisma/debug": "6.10.1" } }, "sha512-4CY5ndKylcsce9Mv+VWp5obbR2/86SHOLVV053pwIkhVtT9C9A83yqiqI/5kJM9T1v1u1qco/bYjDKycmei9HA=="],
|
||||
|
||||
"@sapphire/async-queue": ["@sapphire/async-queue@1.5.5", "", {}, "sha512-cvGzxbba6sav2zZkH8GPf2oGk9yYoD5qrNWdu9fRehifgnFZJMV+nuy2nON2roRO4yQQ+v7MK/Pktl/HgfsUXg=="],
|
||||
|
||||
"@sapphire/shapeshift": ["@sapphire/shapeshift@4.0.0", "", { "dependencies": { "fast-deep-equal": "^3.1.3", "lodash": "^4.17.21" } }, "sha512-d9dUmWVA7MMiKobL3VpLF8P2aeanRTu6ypG2OIaEv/ZHH/SUQ2iHOVyi5wAPjQ+HmnMuL0whK9ez8I/raWbtIg=="],
|
||||
|
||||
"@sapphire/snowflake": ["@sapphire/snowflake@3.5.3", "", {}, "sha512-jjmJywLAFoWeBi1W7994zZyiNWPIiqRRNAmSERxyg93xRGzNYvGjlZ0gR6x0F4gPRi2+0O6S71kOZYyr3cxaIQ=="],
|
||||
|
||||
"@sec-ant/readable-stream": ["@sec-ant/readable-stream@0.4.1", "", {}, "sha512-831qok9r2t8AlxLko40y2ebgSDhenenCatLVeW/uBtnHPyhHOvG0C7TvfgecV+wHzIm5KUICgzmVpWS+IMEAeg=="],
|
||||
|
||||
"@sern/cli": ["@sern/cli@1.4.0", "", { "dependencies": { "@esbuild-kit/cjs-loader": "^2.4.2", "@esbuild-kit/esm-loader": "^2.5.5", "colorette": "2.0.20", "commander": "11.0.0", "dotenv": "^16.3.1", "esbuild": "^0.19.1", "execa": "7.2.0", "find-up": "6.3.0", "glob": "^10.3.3", "ora": "6.3.1", "prompts": "2.4.2", "undici": "5.23.0" }, "bin": { "sern": "dist/index.js" } }, "sha512-IePGYYJvIVwNtnukblYxE2X7hiFivLa/p4UVaMi0XLpZ+Fa3BAdsSiBKRzLtBYWl8J2Se9StLSFwBYQW7ik+/Q=="],
|
||||
|
||||
"@sern/handler": ["@sern/handler@4.2.4", "", { "dependencies": { "@sern/ioc": "^1.1.2", "callsites": "^3.1.0", "cron": "^3.1.7", "deepmerge": "^4.3.1" } }, "sha512-8qnYSwH2x5zhp7YidtDxQZFaQrwYn+YITk4kWrvqOx6b9PVDKtdzkjXd4e7dnI0tdmGuVwJGk6eRl/RnGUVDqw=="],
|
||||
|
||||
"@sern/ioc": ["@sern/ioc@1.1.2", "", {}, "sha512-n84w7n5hB1dl8N6dfSbeYIo0QYORMS1bpG/P7J7GoMNTu8c28EYVZ8uGs3Md9GB09UseOKn3mfv1QBDtRsbb1g=="],
|
||||
|
||||
"@sern/publisher": ["@sern/publisher@1.1.2", "", {}, "sha512-1zh99JZykKUhqHhE75ZXfiLsBtf1WI+NnDCojv8UlpnGBEyzO8xyI1X7PNf6cPKRs4W9XqY3PqTJ+hrqzIsMkg=="],
|
||||
|
||||
"@sindresorhus/merge-streams": ["@sindresorhus/merge-streams@4.0.0", "", {}, "sha512-tlqY9xq5ukxTUZBmoOp+m61cqwQD5pHJtFY3Mn8CA8ps6yghLH/Hw8UPdqg4OLmFW3IFlcXnQNmo/dh8HzXYIQ=="],
|
||||
|
||||
"@types/bun": ["@types/bun@1.2.18", "", { "dependencies": { "bun-types": "1.2.18" } }, "sha512-Xf6RaWVheyemaThV0kUfaAUvCNokFr+bH8Jxp+tTZfx7dAPA8z9ePnP9S9+Vspzuxxx9JRAXhnyccRj3GyCMdQ=="],
|
||||
|
||||
"@types/luxon": ["@types/luxon@3.4.2", "", {}, "sha512-TifLZlFudklWlMBfhubvgqTXRzLDI5pCbGa4P8a3wPyUQSW+1xQ5eDsreP9DWHX3tjq1ke96uYG/nwundroWcA=="],
|
||||
|
||||
"@types/mongodb": ["@types/mongodb@4.0.7", "", { "dependencies": { "mongodb": "*" } }, "sha512-lPUYPpzA43baXqnd36cZ9xxorprybxXDzteVKCPAdp14ppHtFJHnXYvNpmBvtMUTb5fKXVv6sVbzo1LHkWhJlw=="],
|
||||
|
||||
"@types/node": ["@types/node@17.0.45", "", {}, "sha512-w+tIMs3rq2afQdsPJlODhoUEKzFP1ayaoyl1CcnwtIlsVe7K7bA1NGm4s3PraqTLlXnbIN84zuBlxBWo1u9BLw=="],
|
||||
|
||||
"@types/react": ["@types/react@19.1.8", "", { "dependencies": { "csstype": "^3.0.2" } }, "sha512-AwAfQ2Wa5bCx9WP8nZL2uMZWod7J7/JSplxbTmBQ5ms6QpqNYm672H0Vu9ZVKVngQ+ii4R/byguVEUZQyeg44g=="],
|
||||
|
||||
"@types/webidl-conversions": ["@types/webidl-conversions@7.0.3", "", {}, "sha512-CiJJvcRtIgzadHCYXw7dqEnMNRjhGZlYK05Mj9OyktqV8uVT8fD2BFOB7S1uwBE3Kj2Z+4UyPmFw/Ixgw/LAlA=="],
|
||||
|
||||
"@types/whatwg-url": ["@types/whatwg-url@11.0.5", "", { "dependencies": { "@types/webidl-conversions": "*" } }, "sha512-coYR071JRaHa+xoEvvYqvnIHaVqaYrLPbsufM9BF63HkwI5Lgmy2QR8Q5K/lYDYo5AK82wOvSOS0UsLTpTG7uQ=="],
|
||||
|
||||
"@types/ws": ["@types/ws@8.18.1", "", { "dependencies": { "@types/node": "*" } }, "sha512-ThVF6DCVhA8kUGy+aazFQ4kXQ7E1Ty7A3ypFOe0IcJV8O/M511G99AW24irKrW56Wt44yG9+ij8FaqoBGkuBXg=="],
|
||||
|
||||
"@vladfrangu/async_event_emitter": ["@vladfrangu/async_event_emitter@2.4.6", "", {}, "sha512-RaI5qZo6D2CVS6sTHFKg1v5Ohq/+Bo2LZ5gzUEwZ/WkHhwtGTCB/sVLw8ijOkAUxasZ+WshN/Rzj4ywsABJ5ZA=="],
|
||||
|
||||
"ansi-regex": ["ansi-regex@6.1.0", "", {}, "sha512-7HSX4QQb4CspciLpVFwyRe79O3xsIZDDLER21kERQ71oaPodF8jL725AgJMFAYbooIqolJoRLuM81SpeUkpkvA=="],
|
||||
|
||||
"ansi-styles": ["ansi-styles@6.2.1", "", {}, "sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug=="],
|
||||
|
||||
"balanced-match": ["balanced-match@1.0.2", "", {}, "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw=="],
|
||||
|
||||
"base64-js": ["base64-js@1.5.1", "", {}, "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA=="],
|
||||
|
||||
"bl": ["bl@5.1.0", "", { "dependencies": { "buffer": "^6.0.3", "inherits": "^2.0.4", "readable-stream": "^3.4.0" } }, "sha512-tv1ZJHLfTDnXE6tMHv73YgSJaWR2AFuPwMntBe7XL/GBFHnT0CLnsHMogfk5+GzCDC5ZWarSCYaIGATZt9dNsQ=="],
|
||||
|
||||
"boolbase": ["boolbase@1.0.0", "", {}, "sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww=="],
|
||||
|
||||
"brace-expansion": ["brace-expansion@2.0.2", "", { "dependencies": { "balanced-match": "^1.0.0" } }, "sha512-Jt0vHyM+jmUBqojB7E1NIYadt0vI0Qxjxd2TErW94wDz+E2LAm5vKMXXwg6ZZBTHPuUlDgQHKXvjGBdfcF1ZDQ=="],
|
||||
|
||||
"bson": ["bson@6.10.4", "", {}, "sha512-WIsKqkSC0ABoBJuT1LEX+2HEvNmNKKgnTAyd0fL8qzK4SH2i9NXg+t08YtdZp/V9IZ33cxe3iV4yM0qg8lMQng=="],
|
||||
|
||||
"buffer": ["buffer@6.0.3", "", { "dependencies": { "base64-js": "^1.3.1", "ieee754": "^1.2.1" } }, "sha512-FTiCpNxtwiZZHEZbcbTIcZjERVICn9yq/pDFkTl95/AxzD1naBctN7YO68riM/gLSDY7sdrMby8hofADYuuqOA=="],
|
||||
|
||||
"buffer-from": ["buffer-from@1.1.2", "", {}, "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ=="],
|
||||
|
||||
"bun-types": ["bun-types@1.2.18", "", { "dependencies": { "@types/node": "*" }, "peerDependencies": { "@types/react": "^19" } }, "sha512-04+Eha5NP7Z0A9YgDAzMk5PHR16ZuLVa83b26kH5+cp1qZW4F6FmAURngE7INf4tKOvCE69vYvDEwoNl1tGiWw=="],
|
||||
|
||||
"busboy": ["busboy@1.6.0", "", { "dependencies": { "streamsearch": "^1.1.0" } }, "sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA=="],
|
||||
|
||||
"callsites": ["callsites@3.1.0", "", {}, "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ=="],
|
||||
|
||||
"chalk": ["chalk@5.4.1", "", {}, "sha512-zgVZuo2WcZgfUEmsn6eO3kINexW8RAE4maiQ8QNs8CtpPCSyMiYsULR3HQYkm3w8FIA3SberyMJMSldGsW+U3w=="],
|
||||
|
||||
"cli-cursor": ["cli-cursor@4.0.0", "", { "dependencies": { "restore-cursor": "^4.0.0" } }, "sha512-VGtlMu3x/4DOtIUwEkRezxUZ2lBacNJCHash0N0WeZDBS+7Ux1dm3XWAgWYxLJFMMdOeXMHXorshEFhbMSGelg=="],
|
||||
|
||||
"cli-spinners": ["cli-spinners@2.9.2", "", {}, "sha512-ywqV+5MmyL4E7ybXgKys4DugZbX0FC6LnwrhjuykIjnK9k8OQacQ7axGKnjDXWNhns0xot3bZI5h55H8yo9cJg=="],
|
||||
|
||||
"clone": ["clone@1.0.4", "", {}, "sha512-JQHZ2QMW6l3aH/j6xCqQThY/9OH4D/9ls34cgkUBiEeocRTU04tHfKPBsUK1PqZCUQM7GiA0IIXJSuXHI64Kbg=="],
|
||||
|
||||
"color": ["color@4.2.3", "", { "dependencies": { "color-convert": "^2.0.1", "color-string": "^1.9.0" } }, "sha512-1rXeuUUiGGrykh+CeBdu5Ie7OJwinCgQY0bc7GCRxy5xVHy+moaqkpL/jqQq0MtQOeYcrqEz4abc5f0KtU7W4A=="],
|
||||
|
||||
"color-convert": ["color-convert@2.0.1", "", { "dependencies": { "color-name": "~1.1.4" } }, "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ=="],
|
||||
|
||||
"color-name": ["color-name@1.1.4", "", {}, "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA=="],
|
||||
|
||||
"color-string": ["color-string@1.9.1", "", { "dependencies": { "color-name": "^1.0.0", "simple-swizzle": "^0.2.2" } }, "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg=="],
|
||||
|
||||
"colorette": ["colorette@2.0.20", "", {}, "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w=="],
|
||||
|
||||
"commander": ["commander@11.0.0", "", {}, "sha512-9HMlXtt/BNoYr8ooyjjNRdIilOTkVJXB+GhxMTtOKwk0R4j4lS4NpjuqmRxroBfnfTSHQIHQB7wryHhXarNjmQ=="],
|
||||
|
||||
"cron": ["cron@3.5.0", "", { "dependencies": { "@types/luxon": "~3.4.0", "luxon": "~3.5.0" } }, "sha512-0eYZqCnapmxYcV06uktql93wNWdlTmmBFP2iYz+JPVcQqlyFYcn1lFuIk4R54pkOmE7mcldTAPZv6X5XA4Q46A=="],
|
||||
|
||||
"cross-spawn": ["cross-spawn@7.0.6", "", { "dependencies": { "path-key": "^3.1.0", "shebang-command": "^2.0.0", "which": "^2.0.1" } }, "sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA=="],
|
||||
|
||||
"css-select": ["css-select@5.2.2", "", { "dependencies": { "boolbase": "^1.0.0", "css-what": "^6.1.0", "domhandler": "^5.0.2", "domutils": "^3.0.1", "nth-check": "^2.0.1" } }, "sha512-TizTzUddG/xYLA3NXodFM0fSbNizXjOKhqiQQwvhlspadZokn1KDy0NZFS0wuEubIYAV5/c1/lAr0TaaFXEXzw=="],
|
||||
|
||||
"css-what": ["css-what@6.2.2", "", {}, "sha512-u/O3vwbptzhMs3L1fQE82ZSLHQQfto5gyZzwteVIEyeaY5Fc7R4dapF/BvRoSYFeqfBk4m0V1Vafq5Pjv25wvA=="],
|
||||
|
||||
"csstype": ["csstype@3.1.3", "", {}, "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw=="],
|
||||
|
||||
"deepmerge": ["deepmerge@4.3.1", "", {}, "sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A=="],
|
||||
|
||||
"defaults": ["defaults@1.0.4", "", { "dependencies": { "clone": "^1.0.2" } }, "sha512-eFuaLoy/Rxalv2kr+lqMlUnrDWV+3j4pljOIJgLIhI058IQfWJ7vXhyEIHu+HtC738klGALYxOKDO0bQP3tg8A=="],
|
||||
|
||||
"detect-libc": ["detect-libc@2.0.4", "", {}, "sha512-3UDv+G9CsCKO1WKMGw9fwq/SWJYbI0c5Y7LU1AXYoDdbhE2AHQ6N6Nb34sG8Fj7T5APy8qXDCKuuIHd1BR0tVA=="],
|
||||
|
||||
"discord-api-types": ["discord-api-types@0.38.13", "", {}, "sha512-FELWJRgLVQuR7Az8RhdEZE0k6QNjSW9PCUcU1iyP2Gke8HrJmnMceSS9pD93UM64s3tvZzJPajpPLjWZJylf4g=="],
|
||||
|
||||
"discord.js": ["discord.js@14.21.0", "", { "dependencies": { "@discordjs/builders": "^1.11.2", "@discordjs/collection": "1.5.3", "@discordjs/formatters": "^0.6.1", "@discordjs/rest": "^2.5.1", "@discordjs/util": "^1.1.1", "@discordjs/ws": "^1.2.3", "@sapphire/snowflake": "3.5.3", "discord-api-types": "^0.38.1", "fast-deep-equal": "3.1.3", "lodash.snakecase": "4.1.1", "magic-bytes.js": "^1.10.0", "tslib": "^2.6.3", "undici": "6.21.3" } }, "sha512-U5w41cEmcnSfwKYlLv5RJjB8Joa+QJyRwIJz5i/eg+v2Qvv6EYpCRhN9I2Rlf0900LuqSDg8edakUATrDZQncQ=="],
|
||||
|
||||
"dom-serializer": ["dom-serializer@2.0.0", "", { "dependencies": { "domelementtype": "^2.3.0", "domhandler": "^5.0.2", "entities": "^4.2.0" } }, "sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg=="],
|
||||
|
||||
"domelementtype": ["domelementtype@2.3.0", "", {}, "sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw=="],
|
||||
|
||||
"domhandler": ["domhandler@5.0.3", "", { "dependencies": { "domelementtype": "^2.3.0" } }, "sha512-cgwlv/1iFQiFnU96XXgROh8xTeetsnJiDsTc7TYCLFd9+/WNkIqPTxiM/8pSd8VIrhXGTf1Ny1q1hquVqDJB5w=="],
|
||||
|
||||
"domutils": ["domutils@3.2.2", "", { "dependencies": { "dom-serializer": "^2.0.0", "domelementtype": "^2.3.0", "domhandler": "^5.0.3" } }, "sha512-6kZKyUajlDuqlHKVX1w7gyslj9MPIXzIFiz/rGu35uC1wMi+kMhQwGhl4lt9unC9Vb9INnY9Z3/ZA3+FhASLaw=="],
|
||||
|
||||
"dotenv": ["dotenv@16.6.1", "", {}, "sha512-uBq4egWHTcTt33a72vpSG0z3HnPuIl6NqYcTrKEg2azoEyl2hpW0zqlxysq2pK9HlDIHyHyakeYaYnSAwd8bow=="],
|
||||
|
||||
"eastasianwidth": ["eastasianwidth@0.2.0", "", {}, "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA=="],
|
||||
|
||||
"emoji-regex": ["emoji-regex@9.2.2", "", {}, "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg=="],
|
||||
|
||||
"entities": ["entities@4.5.0", "", {}, "sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw=="],
|
||||
|
||||
"esbuild": ["esbuild@0.19.12", "", { "optionalDependencies": { "@esbuild/aix-ppc64": "0.19.12", "@esbuild/android-arm": "0.19.12", "@esbuild/android-arm64": "0.19.12", "@esbuild/android-x64": "0.19.12", "@esbuild/darwin-arm64": "0.19.12", "@esbuild/darwin-x64": "0.19.12", "@esbuild/freebsd-arm64": "0.19.12", "@esbuild/freebsd-x64": "0.19.12", "@esbuild/linux-arm": "0.19.12", "@esbuild/linux-arm64": "0.19.12", "@esbuild/linux-ia32": "0.19.12", "@esbuild/linux-loong64": "0.19.12", "@esbuild/linux-mips64el": "0.19.12", "@esbuild/linux-ppc64": "0.19.12", "@esbuild/linux-riscv64": "0.19.12", "@esbuild/linux-s390x": "0.19.12", "@esbuild/linux-x64": "0.19.12", "@esbuild/netbsd-x64": "0.19.12", "@esbuild/openbsd-x64": "0.19.12", "@esbuild/sunos-x64": "0.19.12", "@esbuild/win32-arm64": "0.19.12", "@esbuild/win32-ia32": "0.19.12", "@esbuild/win32-x64": "0.19.12" }, "bin": { "esbuild": "bin/esbuild" } }, "sha512-aARqgq8roFBj054KvQr5f1sFu0D65G+miZRCuJyJ0G13Zwx7vRar5Zhn2tkQNzIXcBrNVsv/8stehpj+GAjgbg=="],
|
||||
|
||||
"execa": ["execa@9.6.0", "", { "dependencies": { "@sindresorhus/merge-streams": "^4.0.0", "cross-spawn": "^7.0.6", "figures": "^6.1.0", "get-stream": "^9.0.0", "human-signals": "^8.0.1", "is-plain-obj": "^4.1.0", "is-stream": "^4.0.1", "npm-run-path": "^6.0.0", "pretty-ms": "^9.2.0", "signal-exit": "^4.1.0", "strip-final-newline": "^4.0.0", "yoctocolors": "^2.1.1" } }, "sha512-jpWzZ1ZhwUmeWRhS7Qv3mhpOhLfwI+uAX4e5fOcXqwMR7EcJ0pj2kV1CVzHVMX/LphnKWD3LObjZCoJ71lKpHw=="],
|
||||
|
||||
"fast-deep-equal": ["fast-deep-equal@3.1.3", "", {}, "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q=="],
|
||||
|
||||
"figures": ["figures@6.1.0", "", { "dependencies": { "is-unicode-supported": "^2.0.0" } }, "sha512-d+l3qxjSesT4V7v2fh+QnmFnUWv9lSpjarhShNTgBOfA0ttejbQUAlHLitbjkoRiDulW0OPoQPYIGhIC8ohejg=="],
|
||||
|
||||
"find-up": ["find-up@6.3.0", "", { "dependencies": { "locate-path": "^7.1.0", "path-exists": "^5.0.0" } }, "sha512-v2ZsoEuVHYy8ZIlYqwPe/39Cy+cFDzp4dXPaxNvkEuouymu+2Jbz0PxpKarJHYJTmv2HWT3O382qY8l4jMWthw=="],
|
||||
|
||||
"foreground-child": ["foreground-child@3.3.1", "", { "dependencies": { "cross-spawn": "^7.0.6", "signal-exit": "^4.0.1" } }, "sha512-gIXjKqtFuWEgzFRJA9WCQeSJLZDjgJUOMCMzxtvFq/37KojM1BFGufqsCy0r4qSQmYLsZYMeyRqzIWOMup03sw=="],
|
||||
|
||||
"get-stream": ["get-stream@9.0.1", "", { "dependencies": { "@sec-ant/readable-stream": "^0.4.1", "is-stream": "^4.0.1" } }, "sha512-kVCxPF3vQM/N0B1PmoqVUqgHP+EeVjmZSQn+1oCRPxd2P21P2F19lIgbR3HBosbB1PUhOAoctJnfEn2GbN2eZA=="],
|
||||
|
||||
"get-tsconfig": ["get-tsconfig@4.10.1", "", { "dependencies": { "resolve-pkg-maps": "^1.0.0" } }, "sha512-auHyJ4AgMz7vgS8Hp3N6HXSmlMdUyhSUrfBF16w153rxtLIEOE+HGqaBppczZvnHLqQJfiHotCYpNhl0lUROFQ=="],
|
||||
|
||||
"glob": ["glob@10.4.5", "", { "dependencies": { "foreground-child": "^3.1.0", "jackspeak": "^3.1.2", "minimatch": "^9.0.4", "minipass": "^7.1.2", "package-json-from-dist": "^1.0.0", "path-scurry": "^1.11.1" }, "bin": { "glob": "dist/esm/bin.mjs" } }, "sha512-7Bv8RF0k6xjo7d4A/PxYLbUCfb6c+Vpd2/mB2yRDlew7Jb5hEXiCD9ibfO7wpk8i4sevK6DFny9h7EYbM3/sHg=="],
|
||||
|
||||
"he": ["he@1.2.0", "", { "bin": { "he": "bin/he" } }, "sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw=="],
|
||||
|
||||
"human-signals": ["human-signals@8.0.1", "", {}, "sha512-eKCa6bwnJhvxj14kZk5NCPc6Hb6BdsU9DZcOnmQKSnO1VKrfV0zCvtttPZUsBvjmNDn8rpcJfpwSYnHBjc95MQ=="],
|
||||
|
||||
"ieee754": ["ieee754@1.2.1", "", {}, "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA=="],
|
||||
|
||||
"inherits": ["inherits@2.0.4", "", {}, "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ=="],
|
||||
|
||||
"is-arrayish": ["is-arrayish@0.3.2", "", {}, "sha512-eVRqCvVlZbuw3GrM63ovNSNAeA1K16kaR/LRY/92w0zxQ5/1YzwblUX652i4Xs9RwAGjW9d9y6X88t8OaAJfWQ=="],
|
||||
|
||||
"is-fullwidth-code-point": ["is-fullwidth-code-point@3.0.0", "", {}, "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg=="],
|
||||
|
||||
"is-interactive": ["is-interactive@2.0.0", "", {}, "sha512-qP1vozQRI+BMOPcjFzrjXuQvdak2pHNUMZoeG2eRbiSqyvbEf/wQtEOTOX1guk6E3t36RkaqiSt8A/6YElNxLQ=="],
|
||||
|
||||
"is-plain-obj": ["is-plain-obj@4.1.0", "", {}, "sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg=="],
|
||||
|
||||
"is-stream": ["is-stream@4.0.1", "", {}, "sha512-Dnz92NInDqYckGEUJv689RbRiTSEHCQ7wOVeALbkOz999YpqT46yMRIGtSNl2iCL1waAZSx40+h59NV/EwzV/A=="],
|
||||
|
||||
"is-unicode-supported": ["is-unicode-supported@1.3.0", "", {}, "sha512-43r2mRvz+8JRIKnWJ+3j8JtjRKZ6GmjzfaE/qiBJnikNnYv/6bagRJ1kUhNk8R5EX/GkobD+r+sfxCPJsiKBLQ=="],
|
||||
|
||||
"isexe": ["isexe@2.0.0", "", {}, "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw=="],
|
||||
|
||||
"jackspeak": ["jackspeak@3.4.3", "", { "dependencies": { "@isaacs/cliui": "^8.0.2" }, "optionalDependencies": { "@pkgjs/parseargs": "^0.11.0" } }, "sha512-OGlZQpz2yfahA/Rd1Y8Cd9SIEsqvXkLVoSw/cgwhnhFMDbsQFeZYoJJ7bIZBS9BcamUW96asq/npPWugM+RQBw=="],
|
||||
|
||||
"jiti": ["jiti@2.4.2", "", { "bin": { "jiti": "lib/jiti-cli.mjs" } }, "sha512-rg9zJN+G4n2nfJl5MW3BMygZX56zKPNVEYYqq7adpmMh4Jn2QNEwhvQlFy6jPVdcod7txZtKHWnyZiA3a0zP7A=="],
|
||||
|
||||
"kleur": ["kleur@3.0.3", "", {}, "sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w=="],
|
||||
|
||||
"locate-path": ["locate-path@7.2.0", "", { "dependencies": { "p-locate": "^6.0.0" } }, "sha512-gvVijfZvn7R+2qyPX8mAuKcFGDf6Nc61GdvGafQsHL0sBIxfKzA+usWn4GFC/bk+QdwPUD4kWFJLhElipq+0VA=="],
|
||||
|
||||
"lodash": ["lodash@4.17.21", "", {}, "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg=="],
|
||||
|
||||
"lodash.snakecase": ["lodash.snakecase@4.1.1", "", {}, "sha512-QZ1d4xoBHYUeuouhEq3lk3Uq7ldgyFXGBhg04+oRLnIz8o9T65Eh+8YdroUwn846zchkA9yDsDl5CVVaV2nqYw=="],
|
||||
|
||||
"log-symbols": ["log-symbols@5.1.0", "", { "dependencies": { "chalk": "^5.0.0", "is-unicode-supported": "^1.1.0" } }, "sha512-l0x2DvrW294C9uDCoQe1VSU4gf529FkSZ6leBl4TiqZH/e+0R7hSfHQBNut2mNygDgHwvYHfFLn6Oxb3VWj2rA=="],
|
||||
|
||||
"lru-cache": ["lru-cache@10.4.3", "", {}, "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ=="],
|
||||
|
||||
"luxon": ["luxon@3.5.0", "", {}, "sha512-rh+Zjr6DNfUYR3bPwJEnuwDdqMbxZW7LOQfUN4B54+Cl+0o5zaU9RJ6bcidfDtC1cWCZXQ+nvX8bf6bAji37QQ=="],
|
||||
|
||||
"magic-bytes.js": ["magic-bytes.js@1.12.1", "", {}, "sha512-ThQLOhN86ZkJ7qemtVRGYM+gRgR8GEXNli9H/PMvpnZsE44Xfh3wx9kGJaldg314v85m+bFW6WBMaVHJc/c3zA=="],
|
||||
|
||||
"memory-pager": ["memory-pager@1.5.0", "", {}, "sha512-ZS4Bp4r/Zoeq6+NLJpP+0Zzm0pR8whtGPf1XExKLJBAczGMnSi3It14OiNCStjQjM6NU1okjQGSxgEZN8eBYKg=="],
|
||||
|
||||
"merge-stream": ["merge-stream@2.0.0", "", {}, "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w=="],
|
||||
|
||||
"mimic-fn": ["mimic-fn@4.0.0", "", {}, "sha512-vqiC06CuhBTUdZH+RYl8sFrL096vA45Ok5ISO6sE/Mr1jRbGH4Csnhi8f3wKVl7x8mO4Au7Ir9D3Oyv1VYMFJw=="],
|
||||
|
||||
"minimatch": ["minimatch@9.0.5", "", { "dependencies": { "brace-expansion": "^2.0.1" } }, "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow=="],
|
||||
|
||||
"minipass": ["minipass@7.1.2", "", {}, "sha512-qOOzS1cBTWYF4BH8fVePDBOO9iptMnGUEZwNc/cMWnTV2nVLZ7VoNWEPHkYczZA0pdoA7dl6e7FL659nX9S2aw=="],
|
||||
|
||||
"mongodb": ["mongodb@6.17.0", "", { "dependencies": { "@mongodb-js/saslprep": "^1.1.9", "bson": "^6.10.4", "mongodb-connection-string-url": "^3.0.0" }, "peerDependencies": { "@aws-sdk/credential-providers": "^3.188.0", "@mongodb-js/zstd": "^1.1.0 || ^2.0.0", "gcp-metadata": "^5.2.0", "kerberos": "^2.0.1", "mongodb-client-encryption": ">=6.0.0 <7", "snappy": "^7.2.2", "socks": "^2.7.1" }, "optionalPeers": ["@aws-sdk/credential-providers", "@mongodb-js/zstd", "gcp-metadata", "kerberos", "mongodb-client-encryption", "snappy", "socks"] }, "sha512-neerUzg/8U26cgruLysKEjJvoNSXhyID3RvzvdcpsIi2COYM3FS3o9nlH7fxFtefTb942dX3W9i37oPfCVj4wA=="],
|
||||
|
||||
"mongodb-connection-string-url": ["mongodb-connection-string-url@3.0.2", "", { "dependencies": { "@types/whatwg-url": "^11.0.2", "whatwg-url": "^14.1.0 || ^13.0.0" } }, "sha512-rMO7CGo/9BFwyZABcKAWL8UJwH/Kc2x0g72uhDWzG48URRax5TCIcJ7Rc3RZqffZzO/Gwff/jyKwCU9TN8gehA=="],
|
||||
|
||||
"node-html-parser": ["node-html-parser@7.0.1", "", { "dependencies": { "css-select": "^5.1.0", "he": "1.2.0" } }, "sha512-KGtmPY2kS0thCWGK0VuPyOS+pBKhhe8gXztzA2ilAOhbUbxa9homF1bOyKvhGzMLXUoRds9IOmr/v5lr/lqNmA=="],
|
||||
|
||||
"npm-run-path": ["npm-run-path@6.0.0", "", { "dependencies": { "path-key": "^4.0.0", "unicorn-magic": "^0.3.0" } }, "sha512-9qny7Z9DsQU8Ou39ERsPU4OZQlSTP47ShQzuKZ6PRXpYLtIFgl/DEBYEXKlvcEa+9tHVcK8CF81Y2V72qaZhWA=="],
|
||||
|
||||
"nth-check": ["nth-check@2.1.1", "", { "dependencies": { "boolbase": "^1.0.0" } }, "sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w=="],
|
||||
|
||||
"onetime": ["onetime@6.0.0", "", { "dependencies": { "mimic-fn": "^4.0.0" } }, "sha512-1FlR+gjXK7X+AsAHso35MnyN5KqGwJRi/31ft6x0M194ht7S+rWAvd7PHss9xSKMzE0asv1pyIHaJYq+BbacAQ=="],
|
||||
|
||||
"openai": ["openai@5.10.2", "", { "peerDependencies": { "ws": "^8.18.0", "zod": "^3.23.8" }, "optionalPeers": ["ws", "zod"], "bin": { "openai": "bin/cli" } }, "sha512-n+vi74LzHtvlKcDPn9aApgELGiu5CwhaLG40zxLTlFQdoSJCLACORIPC2uVQ3JEYAbqapM+XyRKFy2Thej7bIw=="],
|
||||
|
||||
"ora": ["ora@6.3.1", "", { "dependencies": { "chalk": "^5.0.0", "cli-cursor": "^4.0.0", "cli-spinners": "^2.6.1", "is-interactive": "^2.0.0", "is-unicode-supported": "^1.1.0", "log-symbols": "^5.1.0", "stdin-discarder": "^0.1.0", "strip-ansi": "^7.0.1", "wcwidth": "^1.0.1" } }, "sha512-ERAyNnZOfqM+Ao3RAvIXkYh5joP220yf59gVe2X/cI6SiCxIdi4c9HZKZD8R6q/RDXEje1THBju6iExiSsgJaQ=="],
|
||||
|
||||
"p-limit": ["p-limit@4.0.0", "", { "dependencies": { "yocto-queue": "^1.0.0" } }, "sha512-5b0R4txpzjPWVw/cXXUResoD4hb6U/x9BH08L7nw+GN1sezDzPdxeRvpc9c433fZhBan/wusjbCsqwqm4EIBIQ=="],
|
||||
|
||||
"p-locate": ["p-locate@6.0.0", "", { "dependencies": { "p-limit": "^4.0.0" } }, "sha512-wPrq66Llhl7/4AGC6I+cqxT07LhXvWL08LNXz1fENOw0Ap4sRZZ/gZpTTJ5jpurzzzfS2W/Ge9BY3LgLjCShcw=="],
|
||||
|
||||
"package-json-from-dist": ["package-json-from-dist@1.0.1", "", {}, "sha512-UEZIS3/by4OC8vL3P2dTXRETpebLI2NiI5vIrjaD/5UtrkFX/tNbwjTSRAGC/+7CAo2pIcBaRgWmcBBHcsaCIw=="],
|
||||
|
||||
"parse-ms": ["parse-ms@4.0.0", "", {}, "sha512-TXfryirbmq34y8QBwgqCVLi+8oA3oWx2eAnSn62ITyEhEYaWRlVZ2DvMM9eZbMs/RfxPu/PK/aBLyGj4IrqMHw=="],
|
||||
|
||||
"path-exists": ["path-exists@5.0.0", "", {}, "sha512-RjhtfwJOxzcFmNOi6ltcbcu4Iu+FL3zEj83dk4kAS+fVpTxXLO1b38RvJgT/0QwvV/L3aY9TAnyv0EOqW4GoMQ=="],
|
||||
|
||||
"path-key": ["path-key@3.1.1", "", {}, "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q=="],
|
||||
|
||||
"path-scurry": ["path-scurry@1.11.1", "", { "dependencies": { "lru-cache": "^10.2.0", "minipass": "^5.0.0 || ^6.0.2 || ^7.0.0" } }, "sha512-Xa4Nw17FS9ApQFJ9umLiJS4orGjm7ZzwUrwamcGQuHSzDyth9boKDaycYdDcZDuqYATXw4HFXgaqWTctW/v1HA=="],
|
||||
|
||||
"pretty-ms": ["pretty-ms@9.2.0", "", { "dependencies": { "parse-ms": "^4.0.0" } }, "sha512-4yf0QO/sllf/1zbZWYnvWw3NxCQwLXKzIj0G849LSufP15BXKM0rbD2Z3wVnkMfjdn/CB0Dpp444gYAACdsplg=="],
|
||||
|
||||
"prisma": ["prisma@6.10.1", "", { "dependencies": { "@prisma/config": "6.10.1", "@prisma/engines": "6.10.1" }, "peerDependencies": { "typescript": ">=5.1.0" }, "optionalPeers": ["typescript"], "bin": { "prisma": "build/index.js" } }, "sha512-khhlC/G49E4+uyA3T3H5PRBut486HD2bDqE2+rvkU0pwk9IAqGFacLFUyIx9Uw+W2eCtf6XGwsp+/strUwMNPw=="],
|
||||
|
||||
"prompts": ["prompts@2.4.2", "", { "dependencies": { "kleur": "^3.0.3", "sisteransi": "^1.0.5" } }, "sha512-NxNv/kLguCA7p3jE8oL2aEBsrJWgAakBpgmgK6lpPWV+WuOmY6r2/zbAVnP+T8bQlA0nzHXSJSJW0Hq7ylaD2Q=="],
|
||||
|
||||
"punycode": ["punycode@2.3.1", "", {}, "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg=="],
|
||||
|
||||
"readable-stream": ["readable-stream@3.6.2", "", { "dependencies": { "inherits": "^2.0.3", "string_decoder": "^1.1.1", "util-deprecate": "^1.0.1" } }, "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA=="],
|
||||
|
||||
"resolve-pkg-maps": ["resolve-pkg-maps@1.0.0", "", {}, "sha512-seS2Tj26TBVOC2NIc2rOe2y2ZO7efxITtLZcGSOnHHNOQ7CkiUBfw0Iw2ck6xkIhPwLhKNLS8BO+hEpngQlqzw=="],
|
||||
|
||||
"restore-cursor": ["restore-cursor@4.0.0", "", { "dependencies": { "onetime": "^5.1.0", "signal-exit": "^3.0.2" } }, "sha512-I9fPXU9geO9bHOt9pHHOhOkYerIMsmVaWB0rA2AI9ERh/+x/i7MV5HKBNrg+ljO5eoPVgCcnFuRjJ9uH6I/3eg=="],
|
||||
|
||||
"rockpaperscissors-checker": ["rockpaperscissors-checker@1.2.0", "", {}, "sha512-JfndRzDvMo1st+iK9dKZIEToFDouc+53+whmVFs+zyBOp0zv/sMNY9hUZI5J7ulygmW1fI6QmvRyXmfpN9Sh8Q=="],
|
||||
|
||||
"safe-buffer": ["safe-buffer@5.2.1", "", {}, "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ=="],
|
||||
|
||||
"semver": ["semver@7.7.2", "", { "bin": { "semver": "bin/semver.js" } }, "sha512-RF0Fw+rO5AMf9MAyaRXI4AV0Ulj5lMHqVxxdSgiVbixSCXoEmmX/jk0CuJw4+3SqroYO9VoUh+HcuJivvtJemA=="],
|
||||
|
||||
"sharp": ["sharp@0.34.2", "", { "dependencies": { "color": "^4.2.3", "detect-libc": "^2.0.4", "semver": "^7.7.2" }, "optionalDependencies": { "@img/sharp-darwin-arm64": "0.34.2", "@img/sharp-darwin-x64": "0.34.2", "@img/sharp-libvips-darwin-arm64": "1.1.0", "@img/sharp-libvips-darwin-x64": "1.1.0", "@img/sharp-libvips-linux-arm": "1.1.0", "@img/sharp-libvips-linux-arm64": "1.1.0", "@img/sharp-libvips-linux-ppc64": "1.1.0", "@img/sharp-libvips-linux-s390x": "1.1.0", "@img/sharp-libvips-linux-x64": "1.1.0", "@img/sharp-libvips-linuxmusl-arm64": "1.1.0", "@img/sharp-libvips-linuxmusl-x64": "1.1.0", "@img/sharp-linux-arm": "0.34.2", "@img/sharp-linux-arm64": "0.34.2", "@img/sharp-linux-s390x": "0.34.2", "@img/sharp-linux-x64": "0.34.2", "@img/sharp-linuxmusl-arm64": "0.34.2", "@img/sharp-linuxmusl-x64": "0.34.2", "@img/sharp-wasm32": "0.34.2", "@img/sharp-win32-arm64": "0.34.2", "@img/sharp-win32-ia32": "0.34.2", "@img/sharp-win32-x64": "0.34.2" } }, "sha512-lszvBmB9QURERtyKT2bNmsgxXK0ShJrL/fvqlonCo7e6xBF8nT8xU6pW+PMIbLsz0RxQk3rgH9kd8UmvOzlMJg=="],
|
||||
|
||||
"shebang-command": ["shebang-command@2.0.0", "", { "dependencies": { "shebang-regex": "^3.0.0" } }, "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA=="],
|
||||
|
||||
"shebang-regex": ["shebang-regex@3.0.0", "", {}, "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A=="],
|
||||
|
||||
"signal-exit": ["signal-exit@4.1.0", "", {}, "sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw=="],
|
||||
|
||||
"simple-swizzle": ["simple-swizzle@0.2.2", "", { "dependencies": { "is-arrayish": "^0.3.1" } }, "sha512-JA//kQgZtbuY83m+xT+tXJkmJncGMTFT+C+g2h2R9uxkYIrE2yy9sgmcLhCnw57/WSD+Eh3J97FPEDFnbXnDUg=="],
|
||||
|
||||
"sisteransi": ["sisteransi@1.0.5", "", {}, "sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg=="],
|
||||
|
||||
"source-map": ["source-map@0.6.1", "", {}, "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g=="],
|
||||
|
||||
"source-map-support": ["source-map-support@0.5.21", "", { "dependencies": { "buffer-from": "^1.0.0", "source-map": "^0.6.0" } }, "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w=="],
|
||||
|
||||
"sparse-bitfield": ["sparse-bitfield@3.0.3", "", { "dependencies": { "memory-pager": "^1.0.2" } }, "sha512-kvzhi7vqKTfkh0PZU+2D2PIllw2ymqJKujUcyPMd9Y75Nv4nPbGJZXNhxsgdQab2BmlDct1YnfQCguEvHr7VsQ=="],
|
||||
|
||||
"stdin-discarder": ["stdin-discarder@0.1.0", "", { "dependencies": { "bl": "^5.0.0" } }, "sha512-xhV7w8S+bUwlPTb4bAOUQhv8/cSS5offJuX8GQGq32ONF0ZtDWKfkdomM3HMRA+LhX6um/FZ0COqlwsjD53LeQ=="],
|
||||
|
||||
"streamsearch": ["streamsearch@1.1.0", "", {}, "sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg=="],
|
||||
|
||||
"string-width": ["string-width@5.1.2", "", { "dependencies": { "eastasianwidth": "^0.2.0", "emoji-regex": "^9.2.2", "strip-ansi": "^7.0.1" } }, "sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA=="],
|
||||
|
||||
"string-width-cjs": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="],
|
||||
|
||||
"string_decoder": ["string_decoder@1.3.0", "", { "dependencies": { "safe-buffer": "~5.2.0" } }, "sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA=="],
|
||||
|
||||
"strip-ansi": ["strip-ansi@7.1.0", "", { "dependencies": { "ansi-regex": "^6.0.1" } }, "sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ=="],
|
||||
|
||||
"strip-ansi-cjs": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="],
|
||||
|
||||
"strip-final-newline": ["strip-final-newline@4.0.0", "", {}, "sha512-aulFJcD6YK8V1G7iRB5tigAP4TsHBZZrOV8pjV++zdUwmeV8uzbY7yn6h9MswN62adStNZFuCIx4haBnRuMDaw=="],
|
||||
|
||||
"tr46": ["tr46@5.1.1", "", { "dependencies": { "punycode": "^2.3.1" } }, "sha512-hdF5ZgjTqgAntKkklYw0R03MG2x/bSzTtkxmIRw/sTNV8YXsCJ1tfLAX23lhxhHJlEf3CRCOCGGWw3vI3GaSPw=="],
|
||||
|
||||
"ts-mixer": ["ts-mixer@6.0.4", "", {}, "sha512-ufKpbmrugz5Aou4wcr5Wc1UUFWOLhq+Fm6qa6P0w0K5Qw2yhaUoiWszhCVuNQyNwrlGiscHOmqYoAox1PtvgjA=="],
|
||||
|
||||
"tslib": ["tslib@2.8.1", "", {}, "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w=="],
|
||||
|
||||
"typescript": ["typescript@5.8.3", "", { "bin": { "tsc": "bin/tsc", "tsserver": "bin/tsserver" } }, "sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ=="],
|
||||
|
||||
"undici": ["undici@5.23.0", "", { "dependencies": { "busboy": "^1.6.0" } }, "sha512-1D7w+fvRsqlQ9GscLBwcAJinqcZGHUKjbOmXdlE/v8BvEGXjeWAax+341q44EuTcHXXnfyKNbKRq4Lg7OzhMmg=="],
|
||||
|
||||
"unicorn-magic": ["unicorn-magic@0.3.0", "", {}, "sha512-+QBBXBCvifc56fsbuxZQ6Sic3wqqc3WWaqxs58gvJrcOuN83HGTCwz3oS5phzU9LthRNE9VrJCFCLUgHeeFnfA=="],
|
||||
|
||||
"util-deprecate": ["util-deprecate@1.0.2", "", {}, "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw=="],
|
||||
|
||||
"wcwidth": ["wcwidth@1.0.1", "", { "dependencies": { "defaults": "^1.0.3" } }, "sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg=="],
|
||||
|
||||
"webidl-conversions": ["webidl-conversions@7.0.0", "", {}, "sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g=="],
|
||||
|
||||
"whatwg-url": ["whatwg-url@14.2.0", "", { "dependencies": { "tr46": "^5.1.0", "webidl-conversions": "^7.0.0" } }, "sha512-De72GdQZzNTUBBChsXueQUnPKDkg/5A5zp7pFDuQAj5UFoENpiACU0wlCvzpAGnTkj++ihpKwKyYewn/XNUbKw=="],
|
||||
|
||||
"which": ["which@2.0.2", "", { "dependencies": { "isexe": "^2.0.0" }, "bin": { "node-which": "./bin/node-which" } }, "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA=="],
|
||||
|
||||
"wrap-ansi": ["wrap-ansi@8.1.0", "", { "dependencies": { "ansi-styles": "^6.1.0", "string-width": "^5.0.1", "strip-ansi": "^7.0.1" } }, "sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ=="],
|
||||
|
||||
"wrap-ansi-cjs": ["wrap-ansi@7.0.0", "", { "dependencies": { "ansi-styles": "^4.0.0", "string-width": "^4.1.0", "strip-ansi": "^6.0.0" } }, "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q=="],
|
||||
|
||||
"ws": ["ws@8.18.3", "", { "peerDependencies": { "bufferutil": "^4.0.1", "utf-8-validate": ">=5.0.2" }, "optionalPeers": ["bufferutil", "utf-8-validate"] }, "sha512-PEIGCY5tSlUt50cqyMXfCzX+oOPqN0vuGqWzbcJ2xvnkzkq46oOpz7dQaTDBdfICb4N14+GARUDw2XV2N4tvzg=="],
|
||||
|
||||
"yocto-queue": ["yocto-queue@1.2.1", "", {}, "sha512-AyeEbWOu/TAXdxlV9wmGcR0+yh2j3vYPGOECcIj2S7MkrLyC7ne+oye2BKTItt0ii2PHk4cDy+95+LshzbXnGg=="],
|
||||
|
||||
"yoctocolors": ["yoctocolors@2.1.1", "", {}, "sha512-GQHQqAopRhwU8Kt1DDM8NjibDXHC8eoh1erhGAJPEyveY9qqVeXvVikNKrDz69sHowPMorbPUrH/mx8c50eiBQ=="],
|
||||
|
||||
"@discordjs/rest/@discordjs/collection": ["@discordjs/collection@2.1.1", "", {}, "sha512-LiSusze9Tc7qF03sLCujF5iZp7K+vRNEDBZ86FT9aQAv3vxMLihUvKvpsCWiQ2DJq1tVckopKm1rxomgNUc9hg=="],
|
||||
|
||||
"@discordjs/rest/undici": ["undici@6.21.3", "", {}, "sha512-gBLkYIlEnSp8pFbT64yFgGE6UIB9tAkhukC23PmMDCe5Nd+cRqKxSjw5y54MK2AZMgZfJWMaNE4nYUHgi1XEOw=="],
|
||||
|
||||
"@discordjs/ws/@discordjs/collection": ["@discordjs/collection@2.1.1", "", {}, "sha512-LiSusze9Tc7qF03sLCujF5iZp7K+vRNEDBZ86FT9aQAv3vxMLihUvKvpsCWiQ2DJq1tVckopKm1rxomgNUc9hg=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild": ["esbuild@0.18.20", "", { "optionalDependencies": { "@esbuild/android-arm": "0.18.20", "@esbuild/android-arm64": "0.18.20", "@esbuild/android-x64": "0.18.20", "@esbuild/darwin-arm64": "0.18.20", "@esbuild/darwin-x64": "0.18.20", "@esbuild/freebsd-arm64": "0.18.20", "@esbuild/freebsd-x64": "0.18.20", "@esbuild/linux-arm": "0.18.20", "@esbuild/linux-arm64": "0.18.20", "@esbuild/linux-ia32": "0.18.20", "@esbuild/linux-loong64": "0.18.20", "@esbuild/linux-mips64el": "0.18.20", "@esbuild/linux-ppc64": "0.18.20", "@esbuild/linux-riscv64": "0.18.20", "@esbuild/linux-s390x": "0.18.20", "@esbuild/linux-x64": "0.18.20", "@esbuild/netbsd-x64": "0.18.20", "@esbuild/openbsd-x64": "0.18.20", "@esbuild/sunos-x64": "0.18.20", "@esbuild/win32-arm64": "0.18.20", "@esbuild/win32-ia32": "0.18.20", "@esbuild/win32-x64": "0.18.20" }, "bin": { "esbuild": "bin/esbuild" } }, "sha512-ceqxoedUrcayh7Y7ZX6NdbbDzGROiyVBgC4PriJThBKSVPWnnFHZAkfI1lJT8QFkOwH4qOS2SJkS4wvpGl8BpA=="],
|
||||
|
||||
"@sern/cli/execa": ["execa@7.2.0", "", { "dependencies": { "cross-spawn": "^7.0.3", "get-stream": "^6.0.1", "human-signals": "^4.3.0", "is-stream": "^3.0.0", "merge-stream": "^2.0.0", "npm-run-path": "^5.1.0", "onetime": "^6.0.0", "signal-exit": "^3.0.7", "strip-final-newline": "^3.0.0" } }, "sha512-UduyVP7TLB5IcAQl+OzLyLcS/l32W/GLg+AhHJ+ow40FOk2U3SAllPwR44v4vmdFwIWqpdwxxpQbF1n5ta9seA=="],
|
||||
|
||||
"discord.js/undici": ["undici@6.21.3", "", {}, "sha512-gBLkYIlEnSp8pFbT64yFgGE6UIB9tAkhukC23PmMDCe5Nd+cRqKxSjw5y54MK2AZMgZfJWMaNE4nYUHgi1XEOw=="],
|
||||
|
||||
"figures/is-unicode-supported": ["is-unicode-supported@2.1.0", "", {}, "sha512-mE00Gnza5EEB3Ds0HfMyllZzbBrmLOX3vfWoj9A9PEnTfratQ/BcaJOuMhnkhjXvb2+FkY3VuHqtAGpTPmglFQ=="],
|
||||
|
||||
"npm-run-path/path-key": ["path-key@4.0.0", "", {}, "sha512-haREypq7xkM7ErfgIyA0z+Bj4AGKlMSdlQE2jvJo6huWD1EdkKYV+G/T4nq0YEF2vgTT8kqMFKo1uHn950r4SQ=="],
|
||||
|
||||
"restore-cursor/onetime": ["onetime@5.1.2", "", { "dependencies": { "mimic-fn": "^2.1.0" } }, "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg=="],
|
||||
|
||||
"restore-cursor/signal-exit": ["signal-exit@3.0.7", "", {}, "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ=="],
|
||||
|
||||
"string-width-cjs/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="],
|
||||
|
||||
"string-width-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="],
|
||||
|
||||
"strip-ansi-cjs/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="],
|
||||
|
||||
"wrap-ansi-cjs/ansi-styles": ["ansi-styles@4.3.0", "", { "dependencies": { "color-convert": "^2.0.1" } }, "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg=="],
|
||||
|
||||
"wrap-ansi-cjs/string-width": ["string-width@4.2.3", "", { "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", "strip-ansi": "^6.0.1" } }, "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g=="],
|
||||
|
||||
"wrap-ansi-cjs/strip-ansi": ["strip-ansi@6.0.1", "", { "dependencies": { "ansi-regex": "^5.0.1" } }, "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/android-arm": ["@esbuild/android-arm@0.18.20", "", { "os": "android", "cpu": "arm" }, "sha512-fyi7TDI/ijKKNZTUJAQqiG5T7YjJXgnzkURqmGj13C6dCqckZBLdl4h7bkhHt/t0WP+zO9/zwroDvANaOqO5Sw=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/android-arm64": ["@esbuild/android-arm64@0.18.20", "", { "os": "android", "cpu": "arm64" }, "sha512-Nz4rJcchGDtENV0eMKUNa6L12zz2zBDXuhj/Vjh18zGqB44Bi7MBMSXjgunJgjRhCmKOjnPuZp4Mb6OKqtMHLQ=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/android-x64": ["@esbuild/android-x64@0.18.20", "", { "os": "android", "cpu": "x64" }, "sha512-8GDdlePJA8D6zlZYJV/jnrRAi6rOiNaCC/JclcXpB+KIuvfBN4owLtgzY2bsxnx666XjJx2kDPUmnTtR8qKQUg=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/darwin-arm64": ["@esbuild/darwin-arm64@0.18.20", "", { "os": "darwin", "cpu": "arm64" }, "sha512-bxRHW5kHU38zS2lPTPOyuyTm+S+eobPUnTNkdJEfAddYgEcll4xkT8DB9d2008DtTbl7uJag2HuE5NZAZgnNEA=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/darwin-x64": ["@esbuild/darwin-x64@0.18.20", "", { "os": "darwin", "cpu": "x64" }, "sha512-pc5gxlMDxzm513qPGbCbDukOdsGtKhfxD1zJKXjCCcU7ju50O7MeAZ8c4krSJcOIJGFR+qx21yMMVYwiQvyTyQ=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/freebsd-arm64": ["@esbuild/freebsd-arm64@0.18.20", "", { "os": "freebsd", "cpu": "arm64" }, "sha512-yqDQHy4QHevpMAaxhhIwYPMv1NECwOvIpGCZkECn8w2WFHXjEwrBn3CeNIYsibZ/iZEUemj++M26W3cNR5h+Tw=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/freebsd-x64": ["@esbuild/freebsd-x64@0.18.20", "", { "os": "freebsd", "cpu": "x64" }, "sha512-tgWRPPuQsd3RmBZwarGVHZQvtzfEBOreNuxEMKFcd5DaDn2PbBxfwLcj4+aenoh7ctXcbXmOQIn8HI6mCSw5MQ=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/linux-arm": ["@esbuild/linux-arm@0.18.20", "", { "os": "linux", "cpu": "arm" }, "sha512-/5bHkMWnq1EgKr1V+Ybz3s1hWXok7mDFUMQ4cG10AfW3wL02PSZi5kFpYKrptDsgb2WAJIvRcDm+qIvXf/apvg=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/linux-arm64": ["@esbuild/linux-arm64@0.18.20", "", { "os": "linux", "cpu": "arm64" }, "sha512-2YbscF+UL7SQAVIpnWvYwM+3LskyDmPhe31pE7/aoTMFKKzIc9lLbyGUpmmb8a8AixOL61sQ/mFh3jEjHYFvdA=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/linux-ia32": ["@esbuild/linux-ia32@0.18.20", "", { "os": "linux", "cpu": "ia32" }, "sha512-P4etWwq6IsReT0E1KHU40bOnzMHoH73aXp96Fs8TIT6z9Hu8G6+0SHSw9i2isWrD2nbx2qo5yUqACgdfVGx7TA=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/linux-loong64": ["@esbuild/linux-loong64@0.18.20", "", { "os": "linux", "cpu": "none" }, "sha512-nXW8nqBTrOpDLPgPY9uV+/1DjxoQ7DoB2N8eocyq8I9XuqJ7BiAMDMf9n1xZM9TgW0J8zrquIb/A7s3BJv7rjg=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/linux-mips64el": ["@esbuild/linux-mips64el@0.18.20", "", { "os": "linux", "cpu": "none" }, "sha512-d5NeaXZcHp8PzYy5VnXV3VSd2D328Zb+9dEq5HE6bw6+N86JVPExrA6O68OPwobntbNJ0pzCpUFZTo3w0GyetQ=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/linux-ppc64": ["@esbuild/linux-ppc64@0.18.20", "", { "os": "linux", "cpu": "ppc64" }, "sha512-WHPyeScRNcmANnLQkq6AfyXRFr5D6N2sKgkFo2FqguP44Nw2eyDlbTdZwd9GYk98DZG9QItIiTlFLHJHjxP3FA=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/linux-riscv64": ["@esbuild/linux-riscv64@0.18.20", "", { "os": "linux", "cpu": "none" }, "sha512-WSxo6h5ecI5XH34KC7w5veNnKkju3zBRLEQNY7mv5mtBmrP/MjNBCAlsM2u5hDBlS3NGcTQpoBvRzqBcRtpq1A=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/linux-s390x": ["@esbuild/linux-s390x@0.18.20", "", { "os": "linux", "cpu": "s390x" }, "sha512-+8231GMs3mAEth6Ja1iK0a1sQ3ohfcpzpRLH8uuc5/KVDFneH6jtAJLFGafpzpMRO6DzJ6AvXKze9LfFMrIHVQ=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/linux-x64": ["@esbuild/linux-x64@0.18.20", "", { "os": "linux", "cpu": "x64" }, "sha512-UYqiqemphJcNsFEskc73jQ7B9jgwjWrSayxawS6UVFZGWrAAtkzjxSqnoclCXxWtfwLdzU+vTpcNYhpn43uP1w=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/netbsd-x64": ["@esbuild/netbsd-x64@0.18.20", "", { "os": "none", "cpu": "x64" }, "sha512-iO1c++VP6xUBUmltHZoMtCUdPlnPGdBom6IrO4gyKPFFVBKioIImVooR5I83nTew5UOYrk3gIJhbZh8X44y06A=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/openbsd-x64": ["@esbuild/openbsd-x64@0.18.20", "", { "os": "openbsd", "cpu": "x64" }, "sha512-e5e4YSsuQfX4cxcygw/UCPIEP6wbIL+se3sxPdCiMbFLBWu0eiZOJ7WoD+ptCLrmjZBK1Wk7I6D/I3NglUGOxg=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/sunos-x64": ["@esbuild/sunos-x64@0.18.20", "", { "os": "sunos", "cpu": "x64" }, "sha512-kDbFRFp0YpTQVVrqUd5FTYmWo45zGaXe0X8E1G/LKFC0v8x0vWrhOWSLITcCn63lmZIxfOMXtCfti/RxN/0wnQ=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/win32-arm64": ["@esbuild/win32-arm64@0.18.20", "", { "os": "win32", "cpu": "arm64" }, "sha512-ddYFR6ItYgoaq4v4JmQQaAI5s7npztfV4Ag6NrhiaW0RrnOXqBkgwZLofVTlq1daVTQNhtI5oieTvkRPfZrePg=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/win32-ia32": ["@esbuild/win32-ia32@0.18.20", "", { "os": "win32", "cpu": "ia32" }, "sha512-Wv7QBi3ID/rROT08SABTS7eV4hX26sVduqDOTe1MvGMjNd3EjOz4b7zeexIR62GTIEKrfJXKL9LFxTYgkyeu7g=="],
|
||||
|
||||
"@esbuild-kit/core-utils/esbuild/@esbuild/win32-x64": ["@esbuild/win32-x64@0.18.20", "", { "os": "win32", "cpu": "x64" }, "sha512-kTdfRcSiDfQca/y9QIkng02avJ+NCaQvrMejlsB3RRv5sE9rRoeBPISaZpKxHELzRxZyLvNts1P27W3wV+8geQ=="],
|
||||
|
||||
"@sern/cli/execa/get-stream": ["get-stream@6.0.1", "", {}, "sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg=="],
|
||||
|
||||
"@sern/cli/execa/human-signals": ["human-signals@4.3.1", "", {}, "sha512-nZXjEF2nbo7lIw3mgYjItAfgQXog3OjJogSbKa2CQIIvSGWcKgeJnQlNXip6NglNzYH45nSRiEVimMvYL8DDqQ=="],
|
||||
|
||||
"@sern/cli/execa/is-stream": ["is-stream@3.0.0", "", {}, "sha512-LnQR4bZ9IADDRSkvpqMGvt/tEJWclzklNgSw48V5EAaAeDd6qGvN8ei6k5p0tvxSR171VmGyHuTiAOfxAbr8kA=="],
|
||||
|
||||
"@sern/cli/execa/npm-run-path": ["npm-run-path@5.3.0", "", { "dependencies": { "path-key": "^4.0.0" } }, "sha512-ppwTtiJZq0O/ai0z7yfudtBpWIoxM8yE6nHi1X47eFR2EWORqfbu6CnPlNsjeN683eT0qG6H/Pyf9fCcvjnnnQ=="],
|
||||
|
||||
"@sern/cli/execa/signal-exit": ["signal-exit@3.0.7", "", {}, "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ=="],
|
||||
|
||||
"@sern/cli/execa/strip-final-newline": ["strip-final-newline@3.0.0", "", {}, "sha512-dOESqjYr96iWYylGObzd39EuNTa5VJxyvVAEm5Jnh7KGo75V43Hk1odPQkNDyXNmUR6k+gEiDVXnjB8HJ3crXw=="],
|
||||
|
||||
"restore-cursor/onetime/mimic-fn": ["mimic-fn@2.1.0", "", {}, "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg=="],
|
||||
|
||||
"string-width-cjs/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="],
|
||||
|
||||
"wrap-ansi-cjs/string-width/emoji-regex": ["emoji-regex@8.0.0", "", {}, "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A=="],
|
||||
|
||||
"wrap-ansi-cjs/strip-ansi/ansi-regex": ["ansi-regex@5.0.1", "", {}, "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ=="],
|
||||
|
||||
"@sern/cli/execa/npm-run-path/path-key": ["path-key@4.0.0", "", {}, "sha512-haREypq7xkM7ErfgIyA0z+Bj4AGKlMSdlQE2jvJo6huWD1EdkKYV+G/T4nq0YEF2vgTT8kqMFKo1uHn950r4SQ=="],
|
||||
}
|
||||
}
|
||||
@@ -1,36 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import { ApplicationCommandOptionType } from "discord.js";
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
name: '8ball',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Preguntale a la 8-ball cosas.',
|
||||
//alias : [],
|
||||
options: [{
|
||||
name: "pregunta",
|
||||
description: "Escribe lo que le quieres preguntar.",
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
}],
|
||||
execute: async (ctx, options) => {
|
||||
// yes, the question argument is never used. There is no reason to use it in the code.
|
||||
var eightballwords = [
|
||||
'Probablemente',
|
||||
'Sí',
|
||||
'No',
|
||||
'Dudable',
|
||||
'Como lo veo, todo indica a que sí',
|
||||
'A lo mejor',
|
||||
'No cuentes con ello',
|
||||
'Buena suerte'
|
||||
]
|
||||
await ctx.reply({content: `La bola tiene respuesta: ${eightballwords[Math.floor(Math.random() * eightballwords.length)]}.`, ephemeral: true})
|
||||
},
|
||||
});
|
||||
@@ -1,96 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler';
|
||||
import {
|
||||
ApplicationCommandOptionType,
|
||||
AttachmentBuilder,
|
||||
AutocompleteInteraction,
|
||||
EmbedBuilder,
|
||||
} from 'discord.js';
|
||||
import { publish } from '#plugins';
|
||||
const choices = [
|
||||
'XaviXE',
|
||||
'Paula',
|
||||
'William',
|
||||
'Espejito2500',
|
||||
'Wheelook',
|
||||
'MarioCabrera',
|
||||
'Paticama',
|
||||
'Vinci',
|
||||
'SrIzan',
|
||||
'ItsAdrian',
|
||||
'ByHGT',
|
||||
'Irene',
|
||||
'Boniato64',
|
||||
'Tormentarosa',
|
||||
'H',
|
||||
'SpRaY',
|
||||
];
|
||||
|
||||
export default commandModule({
|
||||
name: 'a',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'A',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'usuario',
|
||||
description: 'Usuario que debería aparecer',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
autocomplete: true,
|
||||
command: {
|
||||
onEvent: [],
|
||||
async execute(ctx: AutocompleteInteraction) {
|
||||
const focusedValue = ctx.options.getFocused();
|
||||
const filtered = choices.filter((choice) =>
|
||||
choice.startsWith(focusedValue)
|
||||
);
|
||||
await ctx.respond(
|
||||
filtered.map((choice) => ({ name: choice, value: choice }))
|
||||
);
|
||||
},
|
||||
},
|
||||
},
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
const option = ctx.interaction.options.getString('usuario');
|
||||
if (!option) {
|
||||
const imagesArray = [
|
||||
'./images/a/XaviXE.png',
|
||||
'./images/a/Paula.png',
|
||||
'./images/a/William.png',
|
||||
'./images/a/Espejito2500.png',
|
||||
'./images/a/Wheelook.png',
|
||||
'./images/a/MarioCabrera.png',
|
||||
'./images/a/Paticama.png',
|
||||
'./images/a/Vinci.png',
|
||||
'./images/a/SrIzan.png',
|
||||
'./images/a/ItsAdrian.png',
|
||||
'./images/a/ByHGT.png',
|
||||
'./images/a/Irene.png',
|
||||
'./images/a/Boniato64.png',
|
||||
'./images/a/Tormentarosa.png',
|
||||
'./images/a/H.png',
|
||||
'./images/a/SpRaY.png',
|
||||
];
|
||||
const images =
|
||||
imagesArray[Math.floor(Math.random() * imagesArray.length)];
|
||||
|
||||
await ctx.reply({ content: 'A', files: [images] });
|
||||
} else {
|
||||
if (choices.indexOf(options[1].getString('usuario', true)) > -1) {
|
||||
const attachmentbuilder = new AttachmentBuilder(
|
||||
`./images/a/${options[1].getString('usuario', true)}.png`
|
||||
);
|
||||
await ctx.reply({ content: 'A', files: [attachmentbuilder] });
|
||||
} else {
|
||||
const embed = new EmbedBuilder()
|
||||
.setTitle('A no encontrado!')
|
||||
.setDescription(
|
||||
`Qué raro, no se ha encontrado ese /a...\nPorqué no pruebas a poner uno del autocompletado?`
|
||||
)
|
||||
.setColor('Red');
|
||||
await ctx.reply({ embeds: [embed], ephemeral: true });
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,192 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import axios from "axios";
|
||||
import { ActionRowBuilder, ApplicationCommandOptionType, ButtonBuilder, ButtonStyle, ComponentType, EmbedBuilder } from "discord.js";
|
||||
import { publish } from "#plugins";
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
name: 'animal',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Enseña un animal',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'gato',
|
||||
description: 'Enseña un gato',
|
||||
type: ApplicationCommandOptionType.Subcommand
|
||||
},
|
||||
{
|
||||
name: 'capybara',
|
||||
description: 'Enseña un capybara',
|
||||
type: ApplicationCommandOptionType.Subcommand
|
||||
},
|
||||
{
|
||||
name: 'zorro',
|
||||
description: 'Enseña un zorro',
|
||||
type: ApplicationCommandOptionType.Subcommand
|
||||
},
|
||||
{
|
||||
name: 'perro',
|
||||
description: 'what the dog doin',
|
||||
type: ApplicationCommandOptionType.Subcommand
|
||||
},
|
||||
{
|
||||
name: 'mapache',
|
||||
description: 'Enseña un mapache',
|
||||
type: ApplicationCommandOptionType.Subcommand
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
switch (options[1].getSubcommand()) {
|
||||
case 'gato': {
|
||||
const request = await axios.get(`https://api.thecatapi.com/v1/images/search?api_key=${process.env.CATAPI}`).then(res => res.data)
|
||||
const embed = new EmbedBuilder()
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setColor("Random")
|
||||
.setImage(request[0].url)
|
||||
.setFooter({text: `ID: ${request[0].id}`})
|
||||
.setTitle('Gato')
|
||||
const row = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId("cat-upvote")
|
||||
.setEmoji("⬆️")
|
||||
.setStyle(ButtonStyle.Success),
|
||||
new ButtonBuilder()
|
||||
.setCustomId("cat-downvote")
|
||||
.setEmoji("⬇️")
|
||||
.setStyle(ButtonStyle.Danger),
|
||||
)
|
||||
const rowdisabled = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId("cat-upvote")
|
||||
.setEmoji("⬆️")
|
||||
.setStyle(ButtonStyle.Success)
|
||||
.setDisabled(true),
|
||||
new ButtonBuilder()
|
||||
.setCustomId("cat-downvote")
|
||||
.setEmoji("⬇️")
|
||||
.setStyle(ButtonStyle.Danger)
|
||||
.setDisabled(true),
|
||||
)
|
||||
const message = await ctx.reply({embeds: [embed], components: [row]})
|
||||
const collector = message.createMessageComponentCollector({time: 30000, componentType: ComponentType.Button})
|
||||
collector.on('collect', async (i) => {
|
||||
await i.deferReply({ephemeral: true})
|
||||
if (i.customId === "cat-upvote") {
|
||||
await axios.post(`https://api.thecatapi.com/v1/votes?api_key=${process.env.CATAPI}`, {
|
||||
"image_id": request[0].id,
|
||||
"sub_id": i.user.id,
|
||||
"value": 1
|
||||
})
|
||||
i.editReply({content: "Has votado positivamente al gato con ID " + "`" + request[0].id + "`"})
|
||||
}
|
||||
if (i.customId === "cat-downvote") {
|
||||
await axios.post(`https://api.thecatapi.com/v1/votes?api_key=${process.env.CATAPI}`, {
|
||||
"image_id": request[0].id,
|
||||
"sub_id": i.user.id,
|
||||
"value": -1
|
||||
})
|
||||
i.editReply({content: "Has votado negativamente al gato con ID " + "`" + request[0].id + "`"})
|
||||
}
|
||||
})
|
||||
collector.on('end', async (i) => {
|
||||
await message.edit({components: [rowdisabled]})
|
||||
})
|
||||
}
|
||||
case 'capybara': {
|
||||
const request = await axios('https://api.capybara-api.xyz/v1/image/random').then(res => res.data)
|
||||
const requestfacts = await axios('https://api.capybara-api.xyz/v1/facts/random').then(res => res.data)
|
||||
const embed = new EmbedBuilder()
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setTitle('Capybara')
|
||||
.setDescription(`Fun fact: ${requestfacts.fact}`)
|
||||
.setColor('Random')
|
||||
.setImage(request.image_urls.medium)
|
||||
.setFooter({text: `ID: ${request.id}`})
|
||||
await ctx.interaction.reply({embeds: [embed]})
|
||||
}
|
||||
case 'zorro': {
|
||||
const request = await axios('https://randomfox.ca/floof/').then(res => res.data)
|
||||
const embed = new EmbedBuilder()
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setTitle('Zorro')
|
||||
.setColor('Random')
|
||||
.setImage(request.image)
|
||||
await ctx.interaction.reply({embeds: [embed]})
|
||||
}
|
||||
case 'perro': {
|
||||
const request = await axios.get(`https://api.thedogapi.com/v1/images/search?api_key=${process.env.DOGAPI}`).then(res => res.data)
|
||||
const embed = new EmbedBuilder()
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setColor("Random")
|
||||
.setImage(request[0].url)
|
||||
.setFooter({text: `ID: ${request[0].id}`})
|
||||
.setTitle('Perro')
|
||||
const row = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId("dog-upvote")
|
||||
.setEmoji("⬆️")
|
||||
.setStyle(ButtonStyle.Success),
|
||||
new ButtonBuilder()
|
||||
.setCustomId("dog-downvote")
|
||||
.setEmoji("⬇️")
|
||||
.setStyle(ButtonStyle.Danger),
|
||||
)
|
||||
const rowdisabled = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId("dog-upvote")
|
||||
.setEmoji("⬆️")
|
||||
.setStyle(ButtonStyle.Success)
|
||||
.setDisabled(true),
|
||||
new ButtonBuilder()
|
||||
.setCustomId("dog-downvote")
|
||||
.setEmoji("⬇️")
|
||||
.setStyle(ButtonStyle.Danger)
|
||||
.setDisabled(true),
|
||||
)
|
||||
const message = await ctx.reply({embeds: [embed], components: [row]})
|
||||
const collector = message.createMessageComponentCollector({time: 30000, componentType: ComponentType.Button})
|
||||
collector.on('collect', async (i) => {
|
||||
await i.deferReply({ephemeral: true})
|
||||
if (i.customId === "dog-upvote") {
|
||||
await axios.post(`https://api.thedogapi.com/v1/votes?api_key=${process.env.DOGAPI}`, {
|
||||
"image_id": request[0].id,
|
||||
"sub_id": i.user.id,
|
||||
"value": 1
|
||||
})
|
||||
i.editReply({content: "Has votado positivamente al gato con ID " + "`" + request[0].id + "`"})
|
||||
}
|
||||
if (i.customId === "dog-downvote") {
|
||||
await axios.post(`https://api.thedogapi.com/v1/votes?api_key=${process.env.DOGAPI}`, {
|
||||
"image_id": request[0].id,
|
||||
"sub_id": i.user.id,
|
||||
"value": -1
|
||||
})
|
||||
i.editReply({content: "Has votado negativamente al gato con ID " + "`" + request[0].id + "`"})
|
||||
}
|
||||
})
|
||||
collector.on('end', async () => {
|
||||
await message.edit({components: [rowdisabled]})
|
||||
})
|
||||
}
|
||||
case 'mapache': {
|
||||
const request = await axios('https://some-random-api.ml/animal/raccoon').then(res => res.data)
|
||||
const embed = new EmbedBuilder()
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setTitle('Mapache')
|
||||
.setDescription(`Fun fact: ${request.fact}`)
|
||||
.setColor('Random')
|
||||
.setImage(request.image)
|
||||
await ctx.interaction.reply({embeds: [embed]})
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,168 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler';
|
||||
import { publish } from '#plugins';
|
||||
import { ANIME } from '@consumet/extensions';
|
||||
import {
|
||||
ActionRowBuilder,
|
||||
ApplicationCommandOptionType,
|
||||
ButtonBuilder,
|
||||
ButtonStyle,
|
||||
ComponentType,
|
||||
EmbedBuilder,
|
||||
} from 'discord.js';
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'busca cosas en gogoanime',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'buscar',
|
||||
description: 'Busca un anime',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'palabra-clave',
|
||||
description: 'La palabra clave',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true,
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
name: 'capitulo',
|
||||
description: 'Mira los links de directo de cualquier capítulo (con su ID)',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'id-serie',
|
||||
description: 'El ID de la serie (búscalo primero)',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: 'id-capitulo',
|
||||
description: 'El ID del capítulo (usa el autocompletado)',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true,
|
||||
autocomplete: true,
|
||||
command: {
|
||||
onEvent: [],
|
||||
execute: async (autocomplete) => {
|
||||
try {
|
||||
const focusedOption = autocomplete.options.getFocused();
|
||||
const gogoanime = new ANIME.Gogoanime();
|
||||
const serieOption = autocomplete.options.getString('id-serie', true)
|
||||
const fetch = await gogoanime.fetchAnimeInfo(serieOption)
|
||||
let choices = fetch.episodes!.filter((choice) => choice.number.toString().startsWith(focusedOption))
|
||||
choices = choices.slice(0, 25)
|
||||
await autocomplete.respond(
|
||||
choices.map((choice) => ({
|
||||
name: choice.number.toString(),
|
||||
value: choice.id.toString(),
|
||||
}))
|
||||
)
|
||||
} catch {
|
||||
await autocomplete.respond([{name: 'Algo malo ha ocurrido! Asegúrate que hayas puesto el ID correctamente', value: 'error'}])
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
],
|
||||
},
|
||||
{
|
||||
name: 'info',
|
||||
description: 'INGLÉS: Consigue información sobre alguna serie con su ID.',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'id',
|
||||
description: 'El nombre de la serie',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
}
|
||||
]
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
const gogoanime = new ANIME.Gogoanime();
|
||||
const doubleslashregex = new RegExp('(?<!:)\/\/+')
|
||||
switch (options[1].getSubcommand()) {
|
||||
case 'buscar': {
|
||||
await ctx.interaction.deferReply()
|
||||
const option = options[1].getString('palabra-clave', true);
|
||||
const search = await gogoanime.search(option);
|
||||
const editedarray = await Promise.all(
|
||||
search.results
|
||||
.map((results) => {
|
||||
return `[${results.title}](<${results.url!.replace(doubleslashregex, '/')}>)`;
|
||||
})
|
||||
.slice(0, 5)
|
||||
);
|
||||
const editedarrayids = await Promise.all(
|
||||
search.results
|
||||
.map((results) => {
|
||||
return `[${results.id}](<${results.url!.replace(doubleslashregex, '/')}>)`;
|
||||
})
|
||||
.slice(0, 5)
|
||||
);
|
||||
const button = new ActionRowBuilder<ButtonBuilder>().addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId('gogoanime-search-toid')
|
||||
.setLabel('Cambiar a ID')
|
||||
.setStyle(ButtonStyle.Secondary)
|
||||
);
|
||||
if (editedarray.length === 0) return await ctx.interaction.editReply({content: 'No se ha encontrado nada con ese resultado de búsqueda, prueba a ser más general o concreto idk'})
|
||||
const message = await ctx.interaction.editReply({
|
||||
content: `Resultados de la búsqueda \`${option}\`:\n${editedarray.join('\n')}`,
|
||||
components: [button],
|
||||
});
|
||||
const collector = message.createMessageComponentCollector({max: 1, componentType: ComponentType.Button, time: 30000})
|
||||
collector.on('collect', async (i) => {
|
||||
if (i.customId !== 'gogoanime-search-toid') return;
|
||||
await ctx.interaction.editReply({
|
||||
content: `Resultados de la búsqueda \`${option}\` (modo ID):\n${editedarrayids.join('\n')}`,
|
||||
components: []
|
||||
})
|
||||
await i.deferUpdate()
|
||||
})
|
||||
} break;
|
||||
case 'capitulo': {
|
||||
const selepisode = options[1].getString('id-capitulo', true)
|
||||
try {
|
||||
const search = await gogoanime.fetchEpisodeServers(selepisode)
|
||||
const arrayed = await Promise.all(search.map((server) => `[${server.name}](<${server.url!.replace(doubleslashregex, '/')}>)`))
|
||||
await ctx.reply({content: `Todos los servidores de \`${selepisode}\` (Vinci no se hace cargo de los enlaces):\n${arrayed.join('\n')}`})
|
||||
} catch {
|
||||
await ctx.reply({content: 'Ha ocurrido un error! Asegúrate que hayas seleccionado bien un capítulo.'})
|
||||
}
|
||||
} break;
|
||||
case 'info': {
|
||||
try {
|
||||
const option = options[1].getString('id', true)
|
||||
const info = await gogoanime.fetchAnimeInfo(option)
|
||||
const embed = new EmbedBuilder()
|
||||
.setColor('Random')
|
||||
.setTitle(`${info.title}`)
|
||||
.setURL(info.url!.replace(doubleslashregex, '/'))
|
||||
.setThumbnail(info.image!)
|
||||
.setFields(
|
||||
{name: 'Géneros', value: `${info.genres!.join(', ')}`},
|
||||
{name: 'Fecha de salida', value: `${info.releaseDate!}`, inline: true},
|
||||
{name: 'Capítulos totales', value: `${info.totalEpisodes!}`, inline: true},
|
||||
{name: '\u200B', value: '\u200B', inline: true},
|
||||
{name: 'Tipo', value: `${info.type!}`, inline: true},
|
||||
)
|
||||
|
||||
await ctx.reply({embeds: [embed]})
|
||||
} catch {
|
||||
await ctx.reply({content: 'Algo malo ha ocurrido, asegúrate que hayas escrito el ID correctamente\nTip: Usa el comando de buscar y conviértelos a ID.'})
|
||||
}
|
||||
} break;
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,15 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import axios from "axios";
|
||||
import { publish } from "#plugins";
|
||||
|
||||
export default commandModule({
|
||||
name: 'chiste',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Enseña un chiste en inglés.',
|
||||
execute: async (ctx, args) => {
|
||||
const jokeJSON = await axios(
|
||||
'https://v2.jokeapi.dev/joke/Programming,Miscellaneous,Spooky,Christmas?blacklistFlags=nsfw,religious,racist,sexist,explicit'
|
||||
).then((res) => res.data);
|
||||
ctx.reply({content: `${jokeJSON.joke || jokeJSON.setup}\n${jokeJSON.delivery || ""}`})
|
||||
}})
|
||||
@@ -1,162 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler';
|
||||
import { publish } from '#plugins';
|
||||
import FormData from 'form-data';
|
||||
import {
|
||||
ActionRowBuilder,
|
||||
ApplicationCommandOptionType,
|
||||
AttachmentBuilder,
|
||||
ButtonBuilder,
|
||||
ButtonStyle,
|
||||
} from 'discord.js';
|
||||
import axios from 'axios';
|
||||
import https from 'node:https'
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
//alias : [],
|
||||
description: 'no one will read this (i hope)',
|
||||
options: [
|
||||
{
|
||||
name: 'heartlocket',
|
||||
description: 'El corazón con una imagen que todos conocemos',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'imagen',
|
||||
description: 'Imagen (jpg o png)',
|
||||
type: ApplicationCommandOptionType.Attachment,
|
||||
required: true,
|
||||
},
|
||||
{
|
||||
name: 'texto',
|
||||
description: 'El texto que poner',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
},
|
||||
],
|
||||
},
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
await ctx.interaction.deferReply();
|
||||
switch (options[1].getSubcommand()) {
|
||||
case 'heartlocket':
|
||||
{
|
||||
try {
|
||||
// get all options
|
||||
const text = options[1].getString('texto');
|
||||
const image = options[1].getAttachment('imagen', true);
|
||||
|
||||
// check file extension of attachment
|
||||
if (
|
||||
!image.contentType!.includes('image/png') &&
|
||||
!image.contentType!.includes('image/jpeg')
|
||||
)
|
||||
return await ctx.interaction.editReply({
|
||||
content:
|
||||
'Tienes que usar una imagen con extensión `.png` o `.jpg`!',
|
||||
});
|
||||
|
||||
// save in a const the content type
|
||||
let fileExtension: string;
|
||||
if (image.contentType!.includes('image/png')) {
|
||||
fileExtension = 'png';
|
||||
} else if (image.contentType!.includes('image/jpeg')) {
|
||||
fileExtension = 'jpg';
|
||||
} else {
|
||||
fileExtension =
|
||||
'this shouldnt be seen, but typescript is sometimes an idiot and it needs an else so it doesnt cry';
|
||||
}
|
||||
|
||||
// upload to tmpfiles so it can be then uploaded to
|
||||
const formDataTemp = new FormData();
|
||||
const imageBinaryTemp = await axios
|
||||
.get(image.url, { responseType: 'arraybuffer' })
|
||||
.then((res) => res.data);
|
||||
const bufferTemp = Buffer.from(imageBinaryTemp, 'binary');
|
||||
formDataTemp.append('file', bufferTemp, `image.${fileExtension}`);
|
||||
const tempupload = await axios
|
||||
.post(
|
||||
`https://tmpfiles.org/api/v1/upload`,
|
||||
formDataTemp,
|
||||
)
|
||||
.then((res) => res.data);
|
||||
|
||||
// compress the image
|
||||
const compress = await axios.get(`https://api.resmush.it/ws.php?img=${(tempupload.data.url as string).replace('https://tmpfiles.org/', 'https://tmpfiles.org/dl/')}&qlty=80`, {
|
||||
httpsAgent: new https.Agent({ rejectUnauthorized: false })
|
||||
}).then(res => res.data)
|
||||
|
||||
// convert image to a binary so it can be sent to the MakeSweet API.
|
||||
const formData = new FormData();
|
||||
const imageBinary = await axios
|
||||
.get((compress.dest as string).replace(/\\\//g, '/'), { responseType: 'arraybuffer' })
|
||||
.then((res) => res.data);
|
||||
const buffer = Buffer.from(imageBinary, 'binary');
|
||||
formData.append('images[]', buffer, `image.${fileExtension}`);
|
||||
|
||||
// make the request to the actual API, but first check if there's text.
|
||||
let request: any;
|
||||
if (text) {
|
||||
request = await axios
|
||||
.post(
|
||||
`https://api.makesweet.com/make/heart-locket?text=${text}`,
|
||||
formData,
|
||||
{
|
||||
headers: {
|
||||
Authorization: process.env.MAKESWEET!,
|
||||
},
|
||||
responseType: 'arraybuffer',
|
||||
}
|
||||
)
|
||||
.then((res) => res.data);
|
||||
} else {
|
||||
request = await axios
|
||||
.post(`https://api.makesweet.com/make/heart-locket`, formData, {
|
||||
headers: {
|
||||
Authorization: process.env.MAKESWEET!,
|
||||
},
|
||||
responseType: 'arraybuffer',
|
||||
})
|
||||
.then((res) => res.data);
|
||||
}
|
||||
|
||||
// make an attachment with the data that the MakeSweet API returned
|
||||
const attachment = new AttachmentBuilder(request, {
|
||||
name: 'makesweet.gif',
|
||||
});
|
||||
|
||||
// finally, send the message
|
||||
const message = await ctx.interaction.editReply({
|
||||
content: 'Tu GIF está listo! 🎉',
|
||||
files: [attachment],
|
||||
});
|
||||
|
||||
// make an image link button
|
||||
const button = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setLabel('Enlace al GIF')
|
||||
.setEmoji('📲')
|
||||
.setURL(`https://api.srizan.dev/misc/download?url=${message.attachments.first()!.url}&type=gif`)
|
||||
.setStyle(ButtonStyle.Link)
|
||||
);
|
||||
await ctx.interaction.editReply({
|
||||
content: 'Tu GIF está listo! 🎉',
|
||||
files: [attachment],
|
||||
components: [button]
|
||||
});
|
||||
|
||||
} catch (e) {
|
||||
await ctx.interaction.editReply({
|
||||
content: `ERROR: He intentado comprimir la imagen, pero no ha sido suficiente. Intenta usar una imagen menos pesada (1mb o menos)\nSi no es eso, probablemente ha ocurrido un error del que no tengo conocimiento.`,
|
||||
});
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,59 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import Canvas from '@napi-rs/canvas';
|
||||
import { ApplicationCommandOptionType, AttachmentBuilder } from 'discord.js';
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
// , '928018226330337280'
|
||||
description: 'Añade a una imagen de megamind "No ...?"',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'texto',
|
||||
description: 'El texto SIN "No" ni "?".',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
const option = options[1].getString('texto', true)
|
||||
|
||||
await ctx.reply({content: 'Cargando...'})
|
||||
|
||||
const before = performance.now()
|
||||
|
||||
const canvas = Canvas.createCanvas(535, 540)
|
||||
const context = canvas.getContext('2d')
|
||||
|
||||
const background = await Canvas.loadImage('./images/megamind/megamind.png')
|
||||
context.drawImage(background, 0, 0, canvas.width, canvas.height)
|
||||
|
||||
const text = `No ${option}?`
|
||||
let fontsize = 60
|
||||
do {
|
||||
fontsize--;
|
||||
context.font = fontsize + "px Impact";
|
||||
} while (context.measureText(text).width > canvas.width)
|
||||
context.fillStyle = 'white'
|
||||
context.textAlign = 'center'
|
||||
context.textBaseline = 'middle'
|
||||
context.fillText(text, canvas.width / 2, canvas.height - 510)
|
||||
|
||||
const encode = await canvas.encode('png')
|
||||
|
||||
const after = performance.now()
|
||||
|
||||
const attachment = new AttachmentBuilder(encode, { name: 'megamind.png' });
|
||||
await ctx.interaction.editReply({
|
||||
content: `Aquí está tu megamind:\nLa generación de imagen ha tardado \`${(after - before).toFixed(2)}ms\`.`,
|
||||
files: [attachment]
|
||||
})
|
||||
},
|
||||
});
|
||||
@@ -1,113 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { ActionRowBuilder, ApplicationCommandOptionType, ButtonBuilder, ButtonStyle, ComponentType, EmbedBuilder, GuildMember } from "discord.js";
|
||||
import { publish } from "#plugins";
|
||||
import rockpaperscissors from "rockpaperscissors-checker";
|
||||
|
||||
export default commandModule({
|
||||
name: 'rps',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Juega piedra papel tijeras con los panas',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'usuario',
|
||||
description: 'El usuario con el que enfrentarse',
|
||||
type: ApplicationCommandOptionType.User,
|
||||
required: true
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
// also the code is mine, I didn't steal from anyone
|
||||
let player1, player2, winner, bothResponded
|
||||
const option = options[1].getMember('usuario') as GuildMember
|
||||
if (ctx.user.id === option.id) {
|
||||
return await ctx.reply({content: `no puedes jugar contigo mismo 💀`, ephemeral: true})
|
||||
} else if (option.user.bot) {
|
||||
return await ctx.reply({content: `no puedes seleccionar a un bot.`, ephemeral: true})
|
||||
}
|
||||
const waitingEmbed = new EmbedBuilder()
|
||||
.setColor('Red')
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setTitle(`Piedra, papel o tijera? <:PauseChamp:1030169623070519388>`)
|
||||
.setDescription(`Esperando a que ambos jugadores eligan...\nJugador 1: ${ctx.user}\nJugador 2: ${option}`)
|
||||
.setFooter({text: `Hay un máximo de 30 segundos para elegir.`})
|
||||
const winEmbed = new EmbedBuilder()
|
||||
.setColor('Green')
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setFooter({text: `Gracias por jugar!`})
|
||||
const tieEmbed = new EmbedBuilder()
|
||||
.setColor('Yellow')
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setTitle(`Ha habido un empate <:Sadge:1015764348385382451>`)
|
||||
.setDescription(`Qué sadge, ha habido un empate...`)
|
||||
.setFooter({text: `Volvemos a intentarlo?`})
|
||||
const timeUpEmbed = new EmbedBuilder()
|
||||
.setColor('Red')
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setTitle(`Se acabó!`)
|
||||
.setDescription(`Uno de los dos jugadores no han respondido en los 30 segundos, así que se acabó la partida!`)
|
||||
.setFooter({text: `Volvemos a intentarlo?`})
|
||||
const buttons = ["Piedra", "Papel", "Tijera"].map(choice => {
|
||||
return new ButtonBuilder()
|
||||
.setLabel(choice)
|
||||
.setCustomId(`rps-${choice.toLowerCase()}`)
|
||||
.setStyle(ButtonStyle.Secondary)
|
||||
})
|
||||
const row = new ActionRowBuilder<ButtonBuilder>();
|
||||
const message = await ctx.interaction.reply({content: `${option}, te han retado a Piedra Papel o Tijera!`, embeds: [waitingEmbed], fetchReply: true, components: [row.setComponents(buttons)]})
|
||||
const collector = message.createMessageComponentCollector({time: 30_000, componentType: ComponentType.Button, filter: (i) => [ctx.user.id, option.id].includes(i.user.id),})
|
||||
collector.on('collect', async (i) => {
|
||||
await i.deferReply({ephemeral: true})
|
||||
if (i.customId === "rps-piedra") {
|
||||
if (i.user.id === ctx.user.id) {
|
||||
player1 = 1
|
||||
await i.editReply({content: `Se ha respondido **piedra** correctamente, buena suerte!\n[Volver al mensaje](${message.url})`})
|
||||
} else if (i.user.id === option.id) {
|
||||
player2 = 1
|
||||
await i.editReply({content: `Se ha respondido **piedra** correctamente, buena suerte!\n[Volver al mensaje](${message.url})`})
|
||||
}
|
||||
} else if (i.customId === "rps-papel") {
|
||||
if (i.user.id === ctx.user.id) {
|
||||
player1 = 2
|
||||
await i.editReply({content: `Se ha respondido **papel** correctamente, buena suerte!\n[Volver al mensaje](${message.url})`})
|
||||
} else if (i.user.id === option.id) {
|
||||
player2 = 2
|
||||
await i.editReply({content: `Se ha respondido **papel** correctamente, buena suerte!\n[Volver al mensaje](${message.url})`})
|
||||
}
|
||||
} else if (i.customId === "rps-tijera") {
|
||||
if (i.user.id === ctx.user.id) {
|
||||
player1 = 3
|
||||
await i.editReply({content: `Se ha respondido **tijera** correctamente, buena suerte!\n[Volver al mensaje](${message.url})`})
|
||||
} else if (i.user.id === option.id) {
|
||||
player2 = 3
|
||||
await i.editReply({content: `Se ha respondido **tijera** correctamente, buena suerte!\n[Volver al mensaje](${message.url})`})
|
||||
}
|
||||
}
|
||||
if (player1 && player2) {
|
||||
const checker = rockpaperscissors(player1, player2)
|
||||
bothResponded = true
|
||||
if (checker === "player1") {
|
||||
winner = ctx.user.username
|
||||
const setDescription = winEmbed.setDescription(`Tenemos resultados!\n**${winner}** ha ganado.`).setTitle(`Ha ganado ${winner}! <:Pog:1030169609178976346>`)
|
||||
await message.edit({embeds: [setDescription], components: [], content: ``})
|
||||
message.react('<:Pog:1030169609178976346>')
|
||||
} else if (checker === "player2") {
|
||||
winner = option.user.username
|
||||
const setDescription = winEmbed.setDescription(`Tenemos resultados!\n**${winner}** ha ganado.`).setTitle(`Ha ganado ${winner}! <:Pog:1030169609178976346>`)
|
||||
await message.edit({embeds: [setDescription], components: [], content: ``})
|
||||
message.react('<:Pog:1030169609178976346>')
|
||||
} else if (checker === "tie") {
|
||||
await message.edit({embeds: [tieEmbed], components: [], content: ``})
|
||||
}
|
||||
}
|
||||
})
|
||||
collector.on('ignore', async (i) => {
|
||||
await i.reply({content: 'No estás jugando!', ephemeral: true})
|
||||
})
|
||||
collector.on('end', async () => {
|
||||
if (bothResponded) return;
|
||||
await message.edit({embeds: [timeUpEmbed], components: [], content: ``})
|
||||
})
|
||||
},
|
||||
});
|
||||
@@ -1,25 +0,0 @@
|
||||
import TicTacToe from 'discord-tictactoe';
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import { ApplicationCommandOptionType, ChatInputCommandInteraction, CommandInteraction, Interaction } from "discord.js";
|
||||
const game = new TicTacToe({language: 'en'})
|
||||
|
||||
export default commandModule({
|
||||
name: 'tictactoe',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'tres en raya',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: "opponent",
|
||||
description: "opponent",
|
||||
type: ApplicationCommandOptionType.User
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
ctx.reply({ content: 'comando desactivado temporalmente :(', ephemeral: true })
|
||||
// game.handleInteraction(ctx.interaction as ChatInputCommandInteraction)
|
||||
},
|
||||
});
|
||||
@@ -1,46 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler';
|
||||
import { AttachmentBuilder } from 'discord.js';
|
||||
import { publish } from '#plugins';
|
||||
import { Readable } from 'node:stream'
|
||||
import { random } from '../../util/randomstring.js';
|
||||
import fs from 'fs';
|
||||
import { execa } from 'execa';
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.CtxMsg,
|
||||
plugins: [publish()],
|
||||
execute: async (ctx) => {
|
||||
await ctx.deferReply({ fetchReply: true })
|
||||
|
||||
const text = ctx.targetMessage.content;
|
||||
const encodedText = encodeURIComponent(text);
|
||||
const url = `https://www.tetyys.com/SAPI4/SAPI4?text=${encodedText}&voice=Adult%20Male%20%232%2C%20American%20English%20(TruVoice)&pitch=140&speed=157`;
|
||||
|
||||
const request = await fetch(url).then(res => res.arrayBuffer())
|
||||
await new Promise(resolve => setTimeout(resolve, 500));
|
||||
|
||||
const randomnumber = random(5)
|
||||
const randomnumber_wav = `bonzi-wav-${randomnumber}.wav`
|
||||
const randomnumber_mp3 = `bonzi-mp3-${randomnumber}.mp3`
|
||||
fs.writeFileSync(`./util/bonzi_temp/${randomnumber_wav}`, new Uint8Array(request))
|
||||
const command = execa('ffmpeg', [
|
||||
'-i', `./util/bonzi_temp/${randomnumber_wav}`,
|
||||
'-vn',
|
||||
`./util/bonzi_temp/${randomnumber_mp3}`
|
||||
], { shell: true })
|
||||
await new Promise((resolve) => {
|
||||
command.on('close', resolve)
|
||||
})
|
||||
|
||||
const stream = new Readable();
|
||||
stream._read = () => {};
|
||||
stream.push(Buffer.from(new Uint8Array(fs.readFileSync(`./util/bonzi_temp/${randomnumber_mp3}`))));
|
||||
stream.push(null)
|
||||
|
||||
const attachment = new AttachmentBuilder(stream, { name: 'bonzied.mp3' })
|
||||
fs.unlinkSync(`./util/bonzi_temp/${randomnumber_mp3}`)
|
||||
fs.unlinkSync(`./util/bonzi_temp/${randomnumber_wav}`)
|
||||
|
||||
await ctx.editReply({ files: [attachment] })
|
||||
},
|
||||
});
|
||||
@@ -1,21 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler';
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Button,
|
||||
execute: async (ctx) => {
|
||||
await ctx.deferReply({ ephemeral: true })
|
||||
const getUserID = await ctx.client.users.fetch((ctx.message.embeds[0].footer!.text).replace('Discord ID: ', ''))
|
||||
|
||||
await getUserID.send({
|
||||
content: `Tu solicitud de entrada al servidor ha sido aceptada correctamente!\nYa puedes entrar al servidor con la IP \`minecraft.maraturing.com\``
|
||||
}).catch(async () => {
|
||||
await ctx.editReply({
|
||||
content: `No se ha podido enviar un DM a ${getUserID} <:Sadge:1015764348385382451>`,
|
||||
})
|
||||
}).then(async () => {
|
||||
await ctx.editReply({
|
||||
content: `Se ha podido enviar un DM a ${getUserID} correctamente! <:Pog:1030169609178976346>`
|
||||
})
|
||||
})
|
||||
},
|
||||
});
|
||||
@@ -1,15 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler';
|
||||
import axios from 'axios';
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Button,
|
||||
plugins: [],
|
||||
execute: async (ctx) => {
|
||||
await ctx.deferReply({ ephemeral: true })
|
||||
const request = await axios.get('https://api.minetools.eu/query/minecraft.maraturing.com/25565').then(res => res.data)
|
||||
|
||||
await ctx.editReply({
|
||||
content: ``
|
||||
})
|
||||
},
|
||||
});
|
||||
@@ -1,35 +0,0 @@
|
||||
import { commandModule, CommandType } from "@sern/handler";
|
||||
import type { APISelectMenuComponent, GuildMember } from "discord.js";
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.StringSelect,
|
||||
name: 'role-menu',
|
||||
async execute(interaction) {
|
||||
await interaction.deferReply({ ephemeral: true });
|
||||
|
||||
const roles = interaction.values;
|
||||
|
||||
const menuRoles: string[] = (
|
||||
interaction.message.components[0].components[0]
|
||||
.data as Readonly<APISelectMenuComponent>
|
||||
// @ts-ignore
|
||||
).options.map((o: { label: string; value: string }) => o.value);
|
||||
|
||||
const member = interaction.member as GuildMember;
|
||||
if (!member) return;
|
||||
|
||||
let content = `Los roles han sido actualizados. Te he dado estos:\n${roles
|
||||
.map((r) => `<@&${r}>`)
|
||||
.join("\n")}`;
|
||||
if (roles.length === 0) content = "Se han actualizado los roles a ninguno o no se han seleccionado roles...";
|
||||
|
||||
const existing = member.roles.cache
|
||||
.filter((r) => r.id !== interaction.guildId)
|
||||
.map((r) => r.id)
|
||||
.filter((r) => !menuRoles.includes(r));
|
||||
|
||||
await member.roles.set(roles.concat(existing)).catch(() => null);
|
||||
|
||||
await interaction.editReply(content);
|
||||
},
|
||||
});
|
||||
@@ -1,69 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler';
|
||||
import { ActionRowBuilder, ButtonBuilder, ButtonStyle, EmbedBuilder } from 'discord.js';
|
||||
import {
|
||||
TextChannel,
|
||||
ThreadAutoArchiveDuration,
|
||||
} from 'discord.js';
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Modal,
|
||||
async execute(modal) {
|
||||
const value = modal.fields.getTextInputValue('sugerenciasInput');
|
||||
function onlySpaces(str: string) {
|
||||
return str.trim().length === 0;
|
||||
}
|
||||
if (onlySpaces(value) === true)
|
||||
return await modal.reply({
|
||||
content: 'Buen intento enviando un mensaje vacío >:D',
|
||||
ephemeral: true,
|
||||
});
|
||||
const embed = new EmbedBuilder()
|
||||
.setColor('Random')
|
||||
.setTitle('Sugerencia')
|
||||
.setAuthor({
|
||||
name: `${modal.user.username}`,
|
||||
iconURL: `${modal.user.displayAvatarURL()}`,
|
||||
})
|
||||
.setDescription(value);
|
||||
const row = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId('suggestions-yes')
|
||||
.setEmoji('✅')
|
||||
.setLabel('0')
|
||||
.setStyle(ButtonStyle.Success),
|
||||
new ButtonBuilder()
|
||||
.setCustomId('suggestions-no')
|
||||
.setEmoji('❎')
|
||||
.setLabel('0')
|
||||
.setStyle(ButtonStyle.Danger),
|
||||
)
|
||||
const row2 = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId('suggestions-yes-who')
|
||||
.setEmoji('✅')
|
||||
.setLabel('Quién')
|
||||
.setStyle(ButtonStyle.Secondary),
|
||||
new ButtonBuilder()
|
||||
.setCustomId('suggestions-no-who')
|
||||
.setEmoji('❎')
|
||||
.setLabel('Quién')
|
||||
.setStyle(ButtonStyle.Secondary),
|
||||
)
|
||||
|
||||
const message1 = await (await modal.client.guilds.fetch(process.env.GUILDID!))
|
||||
.channels.fetch(process.env.SUGGESTIONS_CHANNEL!) as TextChannel;
|
||||
const message2 = await message1.send({ embeds: [embed], components: [row, row2] });
|
||||
message2.startThread({
|
||||
name: `Sugerencia de ${modal.user.username}`,
|
||||
autoArchiveDuration: ThreadAutoArchiveDuration.ThreeDays,
|
||||
reason: 'AUTOMATIZADO: Hilo para discutir sobre la sugerencia.',
|
||||
});
|
||||
modal.reply({
|
||||
content:
|
||||
'¡Enviado!\nRECUERDA QUE NO ESTÁ PERMITIDO ENVIAR MENSAJES VACÍOS.',
|
||||
ephemeral: true,
|
||||
});
|
||||
},
|
||||
});
|
||||
@@ -1,24 +0,0 @@
|
||||
import { commandModule, CommandType } from "@sern/handler";
|
||||
import db from "../../schemas/suggestions.js";
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Button,
|
||||
async execute(interaction) {
|
||||
let finalarray
|
||||
await interaction.deferReply({ephemeral: true})
|
||||
const findeverything = await db.find({msgid: interaction.message.id, upordown: -1})
|
||||
const array = findeverything.filter(message => message.msgid)
|
||||
const fetchedids = await Promise.all(array.map(async (user) => {
|
||||
return interaction.client.users.fetch(user.userid)
|
||||
}))
|
||||
if (fetchedids.length === 0) {
|
||||
finalarray = 'Nadie, de momento'
|
||||
} else {
|
||||
finalarray = fetchedids.join(', ')
|
||||
}
|
||||
await interaction.editReply({
|
||||
content: `Gente que ha hecho downvote:\n${finalarray}`,
|
||||
allowedMentions: {repliedUser: false}
|
||||
})
|
||||
}
|
||||
})
|
||||
@@ -1,50 +0,0 @@
|
||||
import { commandModule, CommandType } from "@sern/handler";
|
||||
import { ActionRowBuilder, ButtonBuilder, ButtonComponentData, ButtonInteraction, ButtonStyle, ComponentType } from "discord.js";
|
||||
import db from "../../schemas/suggestions.js";
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Button,
|
||||
async execute(interaction) {
|
||||
const convertToNumber = Number(interaction.component.label!)
|
||||
const row2 = new ActionRowBuilder<ButtonBuilder>().setComponents(
|
||||
new ButtonBuilder(interaction.message!.components[1].components[0].data as ButtonComponentData),
|
||||
new ButtonBuilder(interaction.message!.components[1].components[1].data as ButtonComponentData)
|
||||
)
|
||||
if (await db.exists({msgid: interaction.message.id, userid: interaction.user.id, upordown: 1})) {
|
||||
await db.findOneAndUpdate({msgid: interaction.message.id, userid: interaction.user.id, upordown: 1}, {upordown: -1}, {returnOriginal: false})
|
||||
// god forbid I use any! I'm literally done with trying to solve this dude
|
||||
const upvoteLabel = JSON.stringify(interaction.message!.components[0].components[0].data) as string
|
||||
const downvotebuttons = new ActionRowBuilder<ButtonBuilder>().setComponents(
|
||||
new ButtonBuilder(interaction.message!.components[0].components[0].data as ButtonComponentData)
|
||||
.setLabel((Number(JSON.parse(upvoteLabel).label) - 1).toString()),
|
||||
new ButtonBuilder()
|
||||
.setCustomId('suggestions-no')
|
||||
.setEmoji('❎')
|
||||
.setLabel((convertToNumber + 1).toString())
|
||||
.setStyle(ButtonStyle.Danger),
|
||||
)
|
||||
await interaction.message.edit({components: [downvotebuttons, row2]})
|
||||
await interaction.deferUpdate()
|
||||
} else if (await db.exists({msgid: interaction.message.id, userid: interaction.user.id, upordown: -1})) {
|
||||
return await interaction.reply({content: 'Ya has hecho downvote.', ephemeral: true})
|
||||
} else {
|
||||
const downvotebuttons = new ActionRowBuilder<ButtonBuilder>().setComponents(
|
||||
new ButtonBuilder(interaction.message!.components[0].components[0].data as ButtonComponentData),
|
||||
new ButtonBuilder()
|
||||
.setCustomId('suggestions-no')
|
||||
.setEmoji('❎')
|
||||
.setLabel((convertToNumber + 1).toString())
|
||||
.setStyle(ButtonStyle.Danger),
|
||||
)
|
||||
|
||||
const addToDB = new db({
|
||||
msgid: interaction.message.id,
|
||||
userid: interaction.user.id,
|
||||
upordown: -1
|
||||
})
|
||||
await addToDB.save()
|
||||
await interaction.message.edit({components: [downvotebuttons, row2]})
|
||||
await interaction.deferUpdate()
|
||||
}
|
||||
}
|
||||
})
|
||||
@@ -1,25 +0,0 @@
|
||||
import { commandModule, CommandType } from "@sern/handler";
|
||||
import { ActionRowBuilder, ButtonBuilder, ButtonInteraction, ButtonStyle, ComponentType } from "discord.js";
|
||||
import db from "../../schemas/suggestions.js";
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Button,
|
||||
async execute(interaction) {
|
||||
let finalarray
|
||||
await interaction.deferReply({ephemeral: true})
|
||||
const findeverything = await db.find({msgid: interaction.message.id, upordown: 1})
|
||||
const array = findeverything.filter(message => message.msgid)
|
||||
const fetchedids = await Promise.all(array.map(async (user) => {
|
||||
return interaction.client.users.fetch(user.userid)
|
||||
}))
|
||||
if (fetchedids.length === 0) {
|
||||
finalarray = 'Nadie, de momento'
|
||||
} else {
|
||||
finalarray = fetchedids.join(', ')
|
||||
}
|
||||
await interaction.editReply({
|
||||
content: `Gente que ha hecho upvote:\n${finalarray}`,
|
||||
allowedMentions: {repliedUser: false}
|
||||
})
|
||||
}
|
||||
})
|
||||
@@ -1,50 +0,0 @@
|
||||
import { commandModule, CommandType } from "@sern/handler";
|
||||
import { ActionRowBuilder, ButtonBuilder, ButtonComponentData, ButtonInteraction, ButtonStyle, ComponentType } from "discord.js";
|
||||
import db from "../../schemas/suggestions.js";
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Button,
|
||||
async execute(interaction) {
|
||||
const convertToNumber = Number(interaction.component.label!)
|
||||
const row2 = new ActionRowBuilder<ButtonBuilder>().setComponents(
|
||||
new ButtonBuilder(interaction.message!.components[1].components[0].data as ButtonComponentData),
|
||||
new ButtonBuilder(interaction.message!.components[1].components[1].data as ButtonComponentData)
|
||||
)
|
||||
if (await db.exists({msgid: interaction.message.id, userid: interaction.user.id, upordown: -1})) {
|
||||
await db.findOneAndUpdate({msgid: interaction.message.id, userid: interaction.user.id, upordown: -1}, {upordown: 1}, {returnOriginal: false})
|
||||
// god forbid I use any! I'm literally done with trying to solve this dude
|
||||
const upvoteLabel = JSON.stringify(interaction.message!.components[0].components[1].data) as string
|
||||
const downvotebuttons = new ActionRowBuilder<ButtonBuilder>().setComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId('suggestions-yes')
|
||||
.setEmoji('✅')
|
||||
.setLabel((convertToNumber + 1).toString())
|
||||
.setStyle(ButtonStyle.Success),
|
||||
new ButtonBuilder(interaction.message!.components[0].components[1].data as ButtonComponentData)
|
||||
.setLabel((Number(JSON.parse(upvoteLabel).label) - 1).toString()),
|
||||
)
|
||||
await interaction.message.edit({components: [downvotebuttons, row2]})
|
||||
await interaction.deferUpdate()
|
||||
} else if (await db.exists({msgid: interaction.message.id, userid: interaction.user.id, upordown: 1})) {
|
||||
return await interaction.reply({content: 'Ya has hecho upvote.', ephemeral: true})
|
||||
} else {
|
||||
const downvotebuttons = new ActionRowBuilder<ButtonBuilder>().setComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId('suggestions-yes')
|
||||
.setEmoji('✅')
|
||||
.setLabel((convertToNumber + 1).toString())
|
||||
.setStyle(ButtonStyle.Success),
|
||||
new ButtonBuilder(interaction.message!.components[0].components[1].data as ButtonComponentData)
|
||||
)
|
||||
|
||||
const addToDB = new db({
|
||||
msgid: interaction.message.id,
|
||||
userid: interaction.user.id,
|
||||
upordown: 1
|
||||
})
|
||||
await addToDB.save()
|
||||
await interaction.message.edit({components: [downvotebuttons, row2]})
|
||||
await interaction.deferUpdate()
|
||||
}
|
||||
}
|
||||
})
|
||||
@@ -1,33 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import { ApplicationCommandOptionType } from "discord.js";
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
name: 'ip',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
//
|
||||
description: 'La IP del servidor de Minecraft',
|
||||
options: [
|
||||
{
|
||||
name: 'usuario',
|
||||
description: 'Menciona al usuario al que va dirigido el comando.',
|
||||
type: ApplicationCommandOptionType.User
|
||||
}
|
||||
],
|
||||
//alias : [],
|
||||
execute: async (ctx, options) => {
|
||||
const usuario = options[1].getMember('usuario');
|
||||
|
||||
if (!usuario) {
|
||||
await ctx.reply({content: "La IP del servidor de Minecraft es `minecraft.maraturing.com`,\nPide acceso con el comando </mcform:1000747672690499594>.", ephemeral: true})
|
||||
} else {
|
||||
await ctx.reply({content: `${usuario}` + ", la IP del servidor de Minecraft es `minecraft.maraturing.com`,\nPide acceso con el comando </mcform:1000747672690499594>."})
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,33 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler';
|
||||
import {
|
||||
ActionRowBuilder,
|
||||
ModalBuilder,
|
||||
TextInputBuilder,
|
||||
TextInputStyle,
|
||||
ModalActionRowComponentBuilder,
|
||||
} from 'discord.js';
|
||||
import { publish } from '#plugins';
|
||||
import { ownerOnly } from '#plugins';
|
||||
|
||||
export default commandModule({
|
||||
name: 'mcform',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Envia el formulario para entrar al servidor.',
|
||||
//alias : [],
|
||||
execute: async (ctx) => {
|
||||
const modal = new ModalBuilder()
|
||||
.setCustomId('mcform-main')
|
||||
.setTitle('Formulario para entrar al servidor');
|
||||
const input = new TextInputBuilder()
|
||||
.setCustomId('mcUsernameInput')
|
||||
.setLabel('Cuál es tu nombre de usuario de Minecraft?')
|
||||
.setStyle(TextInputStyle.Short);
|
||||
const usernameActionRow =
|
||||
new ActionRowBuilder<ModalActionRowComponentBuilder>().addComponents(
|
||||
input
|
||||
);
|
||||
modal.addComponents(usernameActionRow);
|
||||
await ctx.interaction.showModal(modal);
|
||||
},
|
||||
});
|
||||
@@ -1,75 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
import db from '../../schemas/afk.js';
|
||||
import { ApplicationCommandOptionType, EmbedBuilder } from 'discord.js';
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'afk command',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'añadir',
|
||||
description: 'Di que estás AFK o inactivo por la razón que quieras.',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'motivo',
|
||||
description: 'El motivo por el que estarás AFK',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true,
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
name: 'eliminar',
|
||||
description: 'Elimina tu AFK',
|
||||
type: ApplicationCommandOptionType.Subcommand
|
||||
},
|
||||
{
|
||||
name: 'lista',
|
||||
description: 'Listado de todas las personas AFK',
|
||||
type: ApplicationCommandOptionType.Subcommand
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
switch (options[1].getSubcommand()) {
|
||||
case 'añadir': {
|
||||
if (await db.exists({ id: ctx.user.id })) return ctx.reply({ content: 'Ya existes en la base de datos!', ephemeral: true })
|
||||
const reason = options[1].getString('motivo', true);
|
||||
|
||||
await (new db({ id: ctx.user.id, reason: reason })).save()
|
||||
const embed = new EmbedBuilder()
|
||||
.setAuthor({ name: ctx.user.username, iconURL: ctx.user.displayAvatarURL() })
|
||||
.setTitle('AFK añadido!')
|
||||
.setColor('Green')
|
||||
.setDescription(`Razón: ${reason}`)
|
||||
|
||||
await ctx.reply({ embeds: [embed] })
|
||||
} break;
|
||||
case 'eliminar': {
|
||||
if (!await db.exists({ id: ctx.user.id })) return ctx.reply({ content: 'No existes en la base de datos!', ephemeral: true })
|
||||
|
||||
await db.deleteOne({ id: ctx.user.id })
|
||||
|
||||
await ctx.reply('Ok, has sido eliminado correctamente de la base de datos.')
|
||||
} break;
|
||||
case 'lista': {
|
||||
const map = await Promise.all((await db.find()).map(async (doc) => {
|
||||
return `${await ctx.client.users.fetch(doc.id)}`
|
||||
}))
|
||||
|
||||
await ctx.reply({
|
||||
content: `Lista de usuarios AFK:\n${(map.length === 0) ? 'Nadie' : map.join(', ')}`,
|
||||
allowedMentions: { repliedUser: false }
|
||||
})
|
||||
} break;
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,19 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import { ApplicationCommandOptionType } from "discord.js";
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
name: 'askjavi',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'DESACTIVADO: Pregunta a Javi LO QUE SEA!',
|
||||
//alias : [],
|
||||
execute: async (ctx, options) => {
|
||||
await ctx.reply({content: `Este comando ha sido desactivado ya que era para un evento que ya ha ocurrido.\nGracias por haber participado!`, ephemeral: true})
|
||||
},
|
||||
});
|
||||
@@ -1,192 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler';
|
||||
import {
|
||||
ActionRowBuilder,
|
||||
ModalBuilder,
|
||||
TextInputBuilder,
|
||||
TextInputStyle,
|
||||
ModalActionRowComponentBuilder,
|
||||
ButtonBuilder,
|
||||
ButtonStyle,
|
||||
ComponentType,
|
||||
ModalSubmitInteraction,
|
||||
ApplicationCommandOptionType,
|
||||
} from 'discord.js';
|
||||
import { publish } from '#plugins';
|
||||
import { ownerOnly } from '#plugins';
|
||||
import padyama from '../../schemas/padyama.js';
|
||||
import { random } from '../../util/randomstring.js';
|
||||
|
||||
export default commandModule({
|
||||
name: 'askjavi',
|
||||
type: CommandType.Slash,
|
||||
plugins: [
|
||||
// publish(),
|
||||
],
|
||||
description: 'TEMP: Pregunta a Javi LO QUE SEA!',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'new',
|
||||
description: 'Haz una nueva pregunta',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
},
|
||||
{
|
||||
name: 'get',
|
||||
description: 'Mira una pregunta teniendo su ID.',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'id',
|
||||
description: 'El ID de la pregunta',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true,
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
name: 'you',
|
||||
description: 'Todos los IDs de las preguntas que hayas hecho',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
},
|
||||
{
|
||||
name: 'answered',
|
||||
description:
|
||||
'ORGANIZADOR: Todos los IDs de las preguntas que hayas hecho',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'id',
|
||||
description: 'El ID de la pregunta',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true,
|
||||
},
|
||||
],
|
||||
},
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
switch (ctx.interaction.options.getSubcommand()) {
|
||||
case 'new': {
|
||||
const modal = new ModalBuilder()
|
||||
.setCustomId('askjavi')
|
||||
.setTitle('Sugerencias');
|
||||
const input = new TextInputBuilder()
|
||||
.setCustomId('askjavi-prompt')
|
||||
.setLabel('Qué quieres preguntarle?')
|
||||
.setStyle(TextInputStyle.Paragraph);
|
||||
const suggestionsActionRow =
|
||||
new ActionRowBuilder<ModalActionRowComponentBuilder>().addComponents(
|
||||
input
|
||||
);
|
||||
modal.addComponents(suggestionsActionRow);
|
||||
const buttons = new ActionRowBuilder<ButtonBuilder>().addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId('askjavi-buttons-yes')
|
||||
.setLabel('Sí!')
|
||||
.setStyle(ButtonStyle.Success),
|
||||
new ButtonBuilder()
|
||||
.setCustomId('askjavi-buttons-no')
|
||||
.setLabel('Ok mejor no')
|
||||
.setStyle(ButtonStyle.Danger)
|
||||
);
|
||||
const message = await ctx.reply({
|
||||
content: `No puedes enviar sugerencias inútiles o spam.\nSi haces esto, serás descalificado.\nContinuas?`,
|
||||
components: [buttons],
|
||||
ephemeral: true,
|
||||
});
|
||||
const collector = message.createMessageComponentCollector({
|
||||
max: 1,
|
||||
componentType: ComponentType.Button,
|
||||
time: 60_000,
|
||||
});
|
||||
collector.on('collect', async (i) => {
|
||||
if (i.customId === 'askjavi-buttons-yes') {
|
||||
const suggestionid = random(5);
|
||||
await i.showModal(modal);
|
||||
await ctx.interaction.editReply({
|
||||
components: [],
|
||||
});
|
||||
const submitted = (await ctx.interaction
|
||||
.awaitModalSubmit({
|
||||
time: 180000,
|
||||
filter: (i) => i.user.id === ctx.user.id,
|
||||
})
|
||||
.catch((error) => {})) as ModalSubmitInteraction;
|
||||
const db = new padyama({
|
||||
id: i.user.id,
|
||||
user: i.user.username,
|
||||
suggestionid: suggestionid,
|
||||
suggestion: submitted.fields.getTextInputValue('askjavi-prompt'),
|
||||
});
|
||||
await db.save();
|
||||
await submitted.reply({
|
||||
content: `Tu pregunta ha sido registrada en la base de datos correctamente.\nEl ID de esta pregunta es: \`${suggestionid}\`. Se te contactará por DMs cuando se responda la pregunta.\nPuedes ver tus IDs de preguntas con el comando </askjavi you:1040938647001776199>.`,
|
||||
ephemeral: true,
|
||||
});
|
||||
}
|
||||
if (i.customId === 'askjavi-buttons-no') {
|
||||
await ctx.interaction.editReply({
|
||||
content: 'Ok pues...',
|
||||
components: [],
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
case 'get': {
|
||||
const option = options[1].getString('id');
|
||||
const db = await padyama.findOne({ suggestionid: option });
|
||||
if (db?.suggestion !== undefined)
|
||||
return await ctx.reply({
|
||||
content: `La sugerencia es:\n${db?.suggestion}`,
|
||||
ephemeral: true,
|
||||
});
|
||||
else
|
||||
return await ctx.reply({
|
||||
content: `Parece que ese ID no se ha encontrado...`,
|
||||
ephemeral: true,
|
||||
});
|
||||
}
|
||||
case 'you': {
|
||||
const db = await padyama.find({ id: ctx.user.id });
|
||||
await ctx.reply({
|
||||
content: `Los IDs de las preguntas que has hecho:\n${db.map(
|
||||
(doc) => `\`${doc.suggestionid}\``
|
||||
)}`,
|
||||
ephemeral: true,
|
||||
});
|
||||
}
|
||||
case 'answered': {
|
||||
if (ctx.user.id !== '703974042700611634')
|
||||
return await ctx.reply({
|
||||
content: `No puedes usar este comando.`,
|
||||
ephemeral: true,
|
||||
});
|
||||
const option = options[1].getString('id');
|
||||
const db = await padyama.findOne({ suggestionid: option });
|
||||
if (db?.user !== undefined) {
|
||||
try {
|
||||
await (await ctx.user.fetch(db?.id))
|
||||
.send({
|
||||
content: `Hola!\nRespecto al AMA del sevidor de Mara:\nTu pregunta con ID \`${option}\` ha sido respondida correctamente!`,
|
||||
})
|
||||
.then(async () => {
|
||||
await ctx.reply({
|
||||
content: `DM enviado correctamente!`,
|
||||
ephemeral: true,
|
||||
});
|
||||
});
|
||||
} catch {
|
||||
await ctx.reply({
|
||||
content: `Parece que no se ha podido enviar el DM...`,
|
||||
ephemeral: true,
|
||||
});
|
||||
}
|
||||
} else {
|
||||
await ctx.reply({
|
||||
content: `No se ha encontrado el usuario enlazado con el ID en cuestión...`,
|
||||
ephemeral: true,
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,50 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { Context, SlashOptions } from "@sern/handler";
|
||||
import { ActionRowBuilder, ButtonBuilder, ButtonStyle, EmbedBuilder } from "discord.js";
|
||||
import { publish } from "#plugins";
|
||||
|
||||
export default commandModule({
|
||||
name: 'creditos',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Créditos del bot (en inglés)',
|
||||
//alias : [],
|
||||
options: [],
|
||||
execute: async (ctx, options) => {
|
||||
const baseEmbed = new EmbedBuilder()
|
||||
.setColor('Blurple')
|
||||
.setTitle(`Without these people, the bot wouldn't exist!`)
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setFooter({text: `Created by Sr Izan | This list will be expanded`, iconURL: ctx.client.user?.displayAvatarURL()})
|
||||
const page1 = baseEmbed
|
||||
.setDescription(`**Development**\n
|
||||
<@703974042700611634>: Main development.\n
|
||||
<@464397024247152640>: Trusting me and inviting the bot.\n
|
||||
**For helping me out**\n
|
||||
<@182326315813306368>: sern handler dev, helper at WOK, such a cool guy and helper <3\n
|
||||
<@697795666373640213>: sern handler dev, also helper at WOK, helped me out a ton\n
|
||||
*Some people at the D.JS discord*: yeah\n
|
||||
**Motivation**\n
|
||||
<@719678368173523015>: WHAT ARE YOU DOING ON VINCI RN?!?!?!\n
|
||||
<@530870655005097995>: Gave some ideas on the *original* roadmap\n
|
||||
<@678000774441336842>: My good'ol friend, always has been trying new Vinci stuff\n
|
||||
<@758743564879659069>: Believe it or not, this looper has alvays been beta-testing stuff\n
|
||||
<@697146020647403651>: For always thanking all my work\n
|
||||
<@630502288154427414>: he bans everyone on my twitch\n
|
||||
**And, of course, you <3**\n
|
||||
Thanks everyone, this has been an absolute ride, I don't have words to express my appreciation! <:Pepelove:1030904410307563542>
|
||||
`)
|
||||
const buttons = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setLabel('lol')
|
||||
.setURL('https://discord.com/channels/928018226330337280/928018227156643857/1030480463690731530')
|
||||
.setStyle(ButtonStyle.Link),
|
||||
new ButtonBuilder()
|
||||
.setLabel('<3')
|
||||
.setURL('https://discord.com/channels/928018226330337280/1030913456846680134')
|
||||
.setStyle(ButtonStyle.Link)
|
||||
)
|
||||
await ctx.reply({embeds: [page1], components: [buttons], ephemeral: true})
|
||||
},
|
||||
});
|
||||
@@ -1,61 +0,0 @@
|
||||
import { commandModule, CommandType } from "@sern/handler";
|
||||
import { publish } from "#plugins";
|
||||
import { ApplicationCommandOptionType } from "discord.js";
|
||||
import { readFileSync } from "node:fs";
|
||||
import birthdays from "../../schemas/birthdays.js";
|
||||
import { acceptingBirthday } from "#plugins";
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
name: "cumple",
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish(), acceptingBirthday()],
|
||||
description: "Pon tu cumpleaños en la base de datos para ser felicitado!",
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: "fecha",
|
||||
description: "La fecha de tu cumple (D-M) (elige en el autocompletado)",
|
||||
type: ApplicationCommandOptionType.String,
|
||||
autocomplete: true,
|
||||
required: true,
|
||||
command: {
|
||||
onEvent: [],
|
||||
execute: async (autocomplete) => {
|
||||
const focusedValue = autocomplete.options.getFocused();
|
||||
let choices = JSON.parse(
|
||||
String(readFileSync("./util/daysinyear.txt"))
|
||||
) as Array<string>;
|
||||
choices = choices.filter((choice) =>
|
||||
choice.toString().startsWith(focusedValue)
|
||||
);
|
||||
choices = choices.slice(0, 25);
|
||||
await autocomplete.respond(
|
||||
choices.map((choice) => ({
|
||||
name: choice.toString(),
|
||||
value: choice,
|
||||
}))
|
||||
);
|
||||
},
|
||||
},
|
||||
},
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
const option = ctx.interaction.options.getString("fecha")
|
||||
const array = JSON.parse(
|
||||
String(readFileSync("./util/daysinyear.txt"))
|
||||
) as Array<string>;
|
||||
if (!array.includes(option!)) return await ctx.interaction.editReply('Asegúrate que estás eligiendo una fecha del autocompletado!')
|
||||
if (await birthdays.exists({id: ctx.user.id})) return await ctx.interaction.editReply('No puedes poner tu fecha de nuevo!')
|
||||
const db = new birthdays({
|
||||
id: ctx.user.id,
|
||||
date: option,
|
||||
alreadysent: false
|
||||
});
|
||||
await db.save();
|
||||
await ctx.interaction.editReply('Ok, guardado correctamente. No puedes volver a cambiar la fecha.')
|
||||
},
|
||||
});
|
||||
@@ -1,66 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { ApplicationCommandOptionType, ColorResolvable, EmbedBuilder } from 'discord.js';
|
||||
import { publish } from "#plugins";
|
||||
import fs from 'node:fs';
|
||||
import mctags from '../../util/tags/minecraft.json' assert { type: 'json' }
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Preguntas normalmente preguntadas :pepega:',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'minecraft',
|
||||
description: 'Preguntas normalmente preguntadas de Minecraft',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'pregunta',
|
||||
description: 'La pregunta',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
autocomplete: true,
|
||||
required: true,
|
||||
command: {
|
||||
onEvent: [],
|
||||
execute: async (ctx) => {
|
||||
const query = ctx.options.getFocused()
|
||||
const filter = mctags.filter(obj => obj.title.includes(query))
|
||||
await ctx.respond(
|
||||
filter.map(map => ({ name: map.title.toString(), value: map.title.toString() }))
|
||||
)
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
name: 'para',
|
||||
description: 'Menciona a la persona a la que vaya esto.',
|
||||
type: ApplicationCommandOptionType.User,
|
||||
}
|
||||
]
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
switch (options[1].getSubcommand()) {
|
||||
case 'minecraft': {
|
||||
const option = options[1].getString('pregunta', true)
|
||||
const forusr = options[1].getMember('para')
|
||||
const filter = mctags.filter(obj => obj.title.includes(option))[0]
|
||||
|
||||
const embed = new EmbedBuilder()
|
||||
.setAuthor({ name: ctx.user.username, iconURL: ctx.user.displayAvatarURL() })
|
||||
.setColor(filter.color as ColorResolvable)
|
||||
.setTitle(filter.title)
|
||||
.setDescription(filter.text)
|
||||
if (forusr) {
|
||||
await ctx.reply({
|
||||
content: `Esto es para tí ${forusr}:`,
|
||||
embeds: [embed]
|
||||
})
|
||||
} else {
|
||||
await ctx.reply({ embeds: [embed] })
|
||||
}
|
||||
} break;
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,34 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import google from 'googlethis'
|
||||
import { ApplicationCommandOptionType } from 'discord.js';
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Busca cosas en Google.',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'busqueda',
|
||||
description: 'Escribe qué quieres buscar',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true,
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
await ctx.interaction.deferReply()
|
||||
const prompt = options[1].getString('busqueda', true)
|
||||
|
||||
const search = await Promise.all((await google.search(prompt)).results.map(res => {
|
||||
return `[${res.title}](<${res.url}>)`
|
||||
}).slice(0, 5))
|
||||
await ctx.interaction.editReply({
|
||||
content: `Resultados para la búsqueda \`${prompt}\`:\n${search.join('\n')}`
|
||||
})
|
||||
},
|
||||
});
|
||||
@@ -1,60 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import Genius from 'genius-lyrics'
|
||||
import { ActionRowBuilder, ApplicationCommandOptionType, ButtonBuilder, ButtonStyle, EmbedBuilder } from 'discord.js';
|
||||
|
||||
const genius = new Genius.Client(process.env.GENIUS)
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Busca la letra de una canción (Genius)',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'busqueda',
|
||||
description: 'Qué buscar',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true,
|
||||
autocomplete: true,
|
||||
command: {
|
||||
onEvent: [],
|
||||
execute: async (ctx) => {
|
||||
const input = ctx.options.getFocused();
|
||||
const choices = (await genius.songs.search(input)).map(res => {
|
||||
return `${res.title} - ${res.artist.name}|${res.id}`
|
||||
})
|
||||
await ctx.respond(
|
||||
choices.map(choice => {
|
||||
const [title, id] = choice.split('|')
|
||||
return ({name: title, value: id})
|
||||
})
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
await ctx.interaction.deferReply({ ephemeral: true })
|
||||
const prompt = options[1].getString('busqueda', true)
|
||||
|
||||
const result = await genius.songs.get(Number(prompt))
|
||||
|
||||
const embed = new EmbedBuilder()
|
||||
.setTitle(`${result.title} - ${result.artist.name}`)
|
||||
.setColor('Random')
|
||||
.setDescription((await result.lyrics()).slice(0, 3000))
|
||||
const button = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setLabel('URL de Genius')
|
||||
.setStyle(ButtonStyle.Link)
|
||||
.setURL(result.url)
|
||||
)
|
||||
|
||||
await ctx.interaction.editReply({
|
||||
embeds: [embed],
|
||||
components: [button]
|
||||
})
|
||||
},
|
||||
});
|
||||
@@ -1,98 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { createAudioPlayer, createAudioResource, DiscordGatewayAdapterCreator, joinVoiceChannel } from "@discordjs/voice";
|
||||
import got from "got";
|
||||
import { ApplicationCommandOptionType, EmbedBuilder } from "discord.js";
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
name: 'radio',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Reproduce la radio',
|
||||
options: [
|
||||
{
|
||||
name: 'reproducir',
|
||||
description: 'Reproduce una radio de la lista',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
autocomplete: true,
|
||||
required: true,
|
||||
command: {
|
||||
onEvent: [],
|
||||
async execute(ctx){
|
||||
const focusedValue = ctx.options.getFocused();
|
||||
const choices = ['Rock FM', 'Cadena 100', 'Cadena Dial', 'Gensokyo Radio', 'BBC 1', 'RNE 1', 'RNE 5', 'Los 40', 'Flaixbac', 'FlaixFM'];
|
||||
const filtered = choices.filter(choice => choice.startsWith(focusedValue));
|
||||
await ctx.respond(
|
||||
filtered.map(choice => ({ name: choice, value: choice })),
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
const radioname = options[1].getString("reproducir", true)
|
||||
const embed = new EmbedBuilder()
|
||||
.setColor("Green")
|
||||
.setTitle(`Reproduciendo ${radioname} en Vinci Radio.`)
|
||||
.setDescription(`A veces la radio tarda en cargar, sé paciente :'D`);
|
||||
const notFoundEmbed = new EmbedBuilder()
|
||||
.setColor("Red")
|
||||
.setTitle(`Radio ${radioname} no encontrada.`)
|
||||
.setDescription(`La radio no ha sido encontrada, asegúrate que la radio está escogida de la lista.`);
|
||||
|
||||
async function playRadio(radioname: string, isFlaix?: boolean) {
|
||||
const stream = got.stream(radioname)
|
||||
const connection = joinVoiceChannel({adapterCreator: ctx.interaction.guild!.voiceAdapterCreator as DiscordGatewayAdapterCreator, channelId: '1008730592835281009',guildId: '928018226330337280',selfDeaf: true});
|
||||
const resource = createAudioResource(stream, { inlineVolume: true });
|
||||
const player = createAudioPlayer();
|
||||
connection.subscribe(player)
|
||||
player.play(resource)
|
||||
if (isFlaix === true) {
|
||||
resource.volume!.setVolume(0.3)
|
||||
} else {
|
||||
resource.volume!.setVolume(0.7)
|
||||
}
|
||||
await ctx.reply({embeds: [embed], ephemeral: true})
|
||||
}
|
||||
|
||||
switch (radioname) {
|
||||
case 'Rock FM': {
|
||||
playRadio("https://flucast-m04-06.flumotion.com/cope/rockfm.mp3")
|
||||
} break;
|
||||
case 'Cadena 100': {
|
||||
playRadio("https://server8.emitironline.com:18196/stream")
|
||||
} break;
|
||||
case 'Cadena Dial': {
|
||||
playRadio("http://20853.live.streamtheworld.com/CADENADIAL.mp3")
|
||||
} break;
|
||||
case 'BBC 1': {
|
||||
playRadio("http://stream.live.vc.bbcmedia.co.uk/bbc_radio_one")
|
||||
} break;
|
||||
case 'RNE 1': {
|
||||
playRadio("https://crtve--di--crtve-ice--01--cdn.cast.addradio.de/crtve/rne1/main/mp3/high")
|
||||
} break;
|
||||
case 'RNE 5': {
|
||||
playRadio("https://crtve--di--crtve-ice--01--cdn.cast.addradio.de/crtve/rne5/main/mp3/high")
|
||||
} break;
|
||||
case 'Los 40': {
|
||||
playRadio('http://stream.ondaceronoroeste.es:8000/stream')
|
||||
} break;
|
||||
case 'Gensokyo Radio': {
|
||||
playRadio('https://stream.gensokyoradio.net/3')
|
||||
} break;
|
||||
case 'Flaixbac': {
|
||||
playRadio('https://nodo07-cloud01.streaming-pro.com:8005/flaixbac.mp3', true)
|
||||
} break;
|
||||
case 'FlaixFM': {
|
||||
playRadio('https://nodo07-cloud01.streaming-pro.com:8001/flaixfm.mp3', true)
|
||||
} break;
|
||||
default: {
|
||||
await ctx.reply({embeds: [notFoundEmbed], ephemeral: true})
|
||||
} break;
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,37 +0,0 @@
|
||||
import { commandModule, CommandType } from "@sern/handler";
|
||||
import axios, { AxiosError, AxiosResponse } from "axios";
|
||||
import { ApplicationCommandOptionType } from "discord.js";
|
||||
import { publish } from "#plugins";
|
||||
|
||||
export default commandModule({
|
||||
name: "acortar",
|
||||
type: CommandType.Slash,
|
||||
plugins: [
|
||||
publish(),
|
||||
],
|
||||
description: "Acorta una URL a vinci.tk",
|
||||
options: [
|
||||
{
|
||||
name: "url",
|
||||
description: "la URL larga",
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true,
|
||||
},
|
||||
],
|
||||
//alias : [],
|
||||
execute: async (ctx, options) => {
|
||||
const url = options[1].getString("url", true);
|
||||
const request = await axios(
|
||||
`https://vinci.tk/yourls-api.php?signature=${process.env.YOURLS_KEY}&action=shorturl&format=json&url=${url}`,
|
||||
{
|
||||
validateStatus: function (status) {
|
||||
return status === 200 || status === 400;
|
||||
},
|
||||
}
|
||||
).then((res: AxiosResponse) => res.data);
|
||||
ctx.reply({
|
||||
content: `URL acortada: <${request.shorturl}>\nURL original: <${url}>`,
|
||||
ephemeral: true,
|
||||
});
|
||||
},
|
||||
});
|
||||
@@ -1,44 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import { EmbedBuilder } from "discord.js";
|
||||
import axios from "axios";
|
||||
import prettySeconds from 'pretty-seconds-spanish'
|
||||
|
||||
export default commandModule({
|
||||
name: 'stats',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Enseña estadísticas del bot.',
|
||||
//alias : [],
|
||||
options: [],
|
||||
execute: async (ctx, options) => {
|
||||
await ctx.interaction.deferReply({ ephemeral: true })
|
||||
const cpubrand = await axios(`http://192.168.1.79:7271/cpubrand`)
|
||||
const cpucores = await axios(`http://192.168.1.79:7271/cpucores`)
|
||||
const ramtotal = await axios(`http://192.168.1.79:7271/ramtotal`)
|
||||
const ramfree = await axios(`http://192.168.1.79:7271/ramfree`)
|
||||
const dockertotal = await axios(`http://192.168.1.79:7271/dockertotal`)
|
||||
const uptime = prettySeconds(process.uptime())
|
||||
const embed = new EmbedBuilder()
|
||||
.setAuthor({name: `${ctx.user.username}`, iconURL: `${ctx.user.displayAvatarURL()}`})
|
||||
.setTitle(`Estadísticas de Vinci.`)
|
||||
.setThumbnail(`https://i.imgur.com/UwC1x8T.png`)
|
||||
.setURL('https://status.vinci.tk')
|
||||
.setColor('Random')
|
||||
.addFields(
|
||||
{name: "Fabricante de CPU", value: `${cpubrand.data}`, inline: true},
|
||||
{name: `Núcleos de CPU`, value: `${cpucores.data}`, inline: true},
|
||||
{name: '\u200B', value: '\u200B', inline: true},
|
||||
{name: `RAM total`, value: `${ramtotal.data}`, inline: true},
|
||||
{name: `RAM libre`, value: `${ramfree.data}`, inline: true},
|
||||
{name: '\u200B', value: '\u200B', inline: true},
|
||||
{name: 'Contenedores de Docker', value: `${dockertotal.data}`, inline: true},
|
||||
{name: '\u200B', value: '\u200B', inline: true},
|
||||
{name: 'Tiempo encendido', value: `${uptime}`},
|
||||
// {name: '\u200B', value: '\u200B', inline: true},
|
||||
// {name: 'Uptime del servidor', value: `${prettySeconds(`${nodeuptime.data}`)}`}
|
||||
)
|
||||
await ctx.interaction.editReply({embeds: [embed]})
|
||||
},
|
||||
});
|
||||
@@ -1,32 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { ActionRowBuilder, ModalBuilder, TextInputBuilder, TextInputStyle, ModalActionRowComponentBuilder } from 'discord.js'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
|
||||
|
||||
export default commandModule({
|
||||
name: 'sugerencias',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Envia una sugerencia.',
|
||||
//alias : [],
|
||||
execute: async (ctx) => {
|
||||
const modal = new ModalBuilder()
|
||||
.setCustomId('sugerencias')
|
||||
.setTitle('Sugerencias');
|
||||
|
||||
// Create the text input components
|
||||
const input = new TextInputBuilder()
|
||||
.setCustomId('sugerenciasInput')
|
||||
// The label is the prompt the user sees for this input
|
||||
.setLabel("Tienes sugerencias?")
|
||||
// Short means only a single line of text
|
||||
.setStyle(TextInputStyle.Paragraph);
|
||||
// An action row only holds one text input,
|
||||
// so you need one action row per text input.
|
||||
const suggestionsActionRow = new ActionRowBuilder<ModalActionRowComponentBuilder>().addComponents(input);
|
||||
// Add inputs to the modal
|
||||
modal.addComponents(suggestionsActionRow);
|
||||
await ctx.interaction.showModal(modal);
|
||||
}
|
||||
});
|
||||
@@ -1,97 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import axios from 'axios';
|
||||
import { readFileSync } from 'node:fs'
|
||||
import { ActionRowBuilder, ApplicationCommandOptionType, ButtonBuilder, ButtonStyle, ComponentType, EmbedBuilder } from 'discord.js';
|
||||
const choices = ['es', 'en', 'fr', 'de', 'hi', 'it', 'ja', 'ko', 'pl']
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
// , '928018226330337280'
|
||||
description: 'Traduce lo que quieras!',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'frase',
|
||||
description: 'La frase que traducir',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: 'idioma',
|
||||
description: 'El idioma al que quieras traducir',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true,
|
||||
autocomplete: true,
|
||||
command: {
|
||||
onEvent: [],
|
||||
execute: async (interaction) => {
|
||||
const focusedValue = interaction.options.getFocused();
|
||||
const filtered = choices.filter(choice => choice.startsWith(focusedValue))
|
||||
await interaction.respond(
|
||||
filtered.map((choice) => ({
|
||||
name: choice,
|
||||
value: choice,
|
||||
}))
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
const langToTranslate = options[1].getString('idioma', true)
|
||||
const stringToTranslate = options[1].getString('frase', true)
|
||||
if (choices.indexOf(langToTranslate) === -1)
|
||||
return ctx.reply({content: 'Elige un idioma del autocompletado.'})
|
||||
|
||||
await ctx.interaction.deferReply()
|
||||
|
||||
const before = performance.now()
|
||||
|
||||
const request = await axios.post('https://translate.nvda.es/translate',
|
||||
{
|
||||
q: stringToTranslate,
|
||||
source: "auto",
|
||||
target: langToTranslate,
|
||||
format: "text",
|
||||
api_key: ""
|
||||
},
|
||||
{
|
||||
headers: {
|
||||
'Content-Type': 'application/json'
|
||||
}
|
||||
}
|
||||
).then(res => res.data)
|
||||
|
||||
const button = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId('translate-original')
|
||||
.setLabel('Texto original')
|
||||
.setStyle(ButtonStyle.Primary)
|
||||
)
|
||||
|
||||
const after = performance.now()
|
||||
|
||||
const embed = new EmbedBuilder()
|
||||
.setAuthor({name: ctx.user.username, iconURL: ctx.user.displayAvatarURL()})
|
||||
.setTitle(`La traducción pedida. He tardado \`${(after - before).toFixed(2)}ms\`.`)
|
||||
.setDescription(request.translatedText as string)
|
||||
.setFooter({text: 'Traducido por LibreTranslate'})
|
||||
|
||||
const message = await ctx.interaction.editReply({embeds: [embed], components: [button]})
|
||||
const collector = message.createMessageComponentCollector({componentType: ComponentType.Button, time: 60_000})
|
||||
|
||||
collector.on('collect', async (i) => {
|
||||
if (i.customId !== 'translate-original') return
|
||||
|
||||
await i.reply({content: `La traducción original es:\n\`\`\`${stringToTranslate}\`\`\``, ephemeral: true})
|
||||
})
|
||||
},
|
||||
});
|
||||
@@ -1,17 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import prettySeconds from 'pretty-seconds-spanish'
|
||||
|
||||
export default commandModule({
|
||||
name: 'uptime',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'Enseña el tiempo que ha estado encendido el bot.',
|
||||
//alias : [],
|
||||
options: [],
|
||||
execute: async (ctx, options) => {
|
||||
// const uptime = prettyMilliseconds(ctx.client.uptime!)
|
||||
const uptime = prettySeconds(process.uptime())
|
||||
await ctx.reply(`El bot lleva encendido ${uptime}`);
|
||||
},
|
||||
});
|
||||
@@ -1,36 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";;
|
||||
import { ApplicationCommandOptionType, EmbedBuilder, GuildMember, TextChannel } from 'discord.js'
|
||||
|
||||
export default commandModule({
|
||||
name: 'ban',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish(), ownerOnly()],
|
||||
description: 'ADMIN: Banea usuarios.',
|
||||
options: [{
|
||||
name: 'usuario',
|
||||
description: 'Escribe un usuario.',
|
||||
type: ApplicationCommandOptionType.User,
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: 'razon',
|
||||
description: 'Escribe la razón.',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
}],
|
||||
//alias : [],
|
||||
execute: async (ctx, options) => {
|
||||
try {
|
||||
const userToBan = options[1].getMember('usuario') as GuildMember
|
||||
const reason = options[1].getString('razon') as string
|
||||
userToBan.ban({reason: reason})
|
||||
const sendToMods = ctx.client.guilds.cache.get(process.env.GUILDID!)!.channels.cache.get(process.env.MODLOGS_CHANNEL!) as TextChannel
|
||||
await sendToMods.send({content: `Se ha baneado a ${userToBan}.\nBan efectuado por ${ctx.user} con razón "${reason}."`})
|
||||
await ctx.reply({content: 'Baneado correctamente!', ephemeral: true})
|
||||
} catch {
|
||||
await ctx.reply({content: `ERROR: No puedo hacer este comando porque a lo mejor soy inferior que el rol de esa persona o estoy usándolo contra admins.`})
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,42 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "../../plugins/index.js";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import { ApplicationCommandOptionType, TextChannel } from "discord.js";
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
name: 'eliminarmensaje',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish(), ownerOnly()],
|
||||
description: 'ADMIN: Elimina comandos por su ID.',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'canal',
|
||||
type: ApplicationCommandOptionType.Channel,
|
||||
description: 'El canal de texto.',
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: 'id',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
description: 'El ID del mensaje.',
|
||||
required: true
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
try {
|
||||
const idMensaje = options[1].getString('id', true);
|
||||
const guildId = ctx.guild!.id
|
||||
const guild = await ctx.client.guilds.fetch(guildId);
|
||||
const channel = await guild.channels.fetch(ctx.channel!.id);
|
||||
(await (channel as TextChannel).messages.fetch(idMensaje)).delete();
|
||||
await ctx.reply({content: 'Mensaje eliminado correctamente.', ephemeral: true});
|
||||
} catch {
|
||||
await ctx.reply({content: `ERROR: No se ha podido eliminar el mensaje, asegúrate que estás usando el ID y el canal correcto.`})
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,38 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";;
|
||||
import { ApplicationCommandOptionType, EmbedBuilder, GuildMember, TextChannel } from 'discord.js'
|
||||
|
||||
export default commandModule({
|
||||
name: 'kick',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish(), ownerOnly()],
|
||||
description: 'ADMIN: Expulsa usuarios.',
|
||||
options: [
|
||||
{
|
||||
name: 'usuario',
|
||||
description: 'Escribe un usuario.',
|
||||
type: ApplicationCommandOptionType.User,
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: 'razon',
|
||||
description: 'Escribe la razón.',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
}
|
||||
],
|
||||
//alias : [],
|
||||
execute: async (ctx, options) => {
|
||||
try {
|
||||
const userToKick = options[1].getMember('usuario');
|
||||
const reason = options[1].getString('razon') as string;
|
||||
(userToKick as GuildMember).kick(reason)
|
||||
const sendToMods = ctx.client.guilds.cache.get(process.env.GUILDID!)!.channels.cache.get(process.env.MODLOGS_CHANNEL!) as TextChannel
|
||||
await sendToMods!.send({content: `Se ha expulsado a ${userToKick}.\nKick efectuado por ${ctx.user} con razón "${reason}."`})
|
||||
await ctx.reply({content: 'Expulsado correctamente!'})
|
||||
} catch {
|
||||
await ctx.reply({content: `ERROR: No puedo hacer este comando porque a lo mejor soy inferior que el rol de esa persona o estoy usándolo contra admins.`})
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,32 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";;
|
||||
import { ApplicationCommandOptionType, TextChannel } from 'discord.js'
|
||||
|
||||
export default commandModule({
|
||||
name: 'prune',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish(), ownerOnly()],
|
||||
description: 'ADMIN: Elimina hasta 100 mensajes',
|
||||
options: [{
|
||||
name: 'numero',
|
||||
description: 'Escribe un número',
|
||||
type: ApplicationCommandOptionType.Number,
|
||||
required: true,
|
||||
min_value: 1,
|
||||
max_value: 100
|
||||
}],
|
||||
//alias : [],
|
||||
execute: async (ctx, options) => {
|
||||
try {
|
||||
const amount = options[1].getNumber('numero', true) as number
|
||||
(ctx.channel as TextChannel).bulkDelete(amount).catch(err => {
|
||||
console.error(err);
|
||||
ctx.reply({content: 'Ha habido un error eliminando mensajes! (mira la consola, Sr Izan)', ephemeral: true});});
|
||||
await ctx.reply({content: `Se han eliminado ${amount} mensajes.`})
|
||||
const sendToMods = ctx.client.guilds.cache.get(process.env.GUILDID!)!.channels.cache.get(process.env.MODLOGS_CHANNEL!) as TextChannel
|
||||
await sendToMods.send({content: `Se han eliminado ${amount} mensajes en ${ctx.channel}\nEfectuado por ${ctx.user}.`})
|
||||
} catch {
|
||||
ctx.reply({content: 'Ha habido un error eliminando mensajes! Error reportado automáticamente.', ephemeral: true})};
|
||||
}
|
||||
});
|
||||
@@ -1,40 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import { ApplicationCommandOptionType, TextChannel } from "discord.js";
|
||||
|
||||
export default commandModule({
|
||||
name: 'slowmode',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish(), ownerOnly()],
|
||||
description: 'ADMIN: Pon modo lento a canales de texto',
|
||||
options: [
|
||||
{
|
||||
name: "segundos",
|
||||
description: "Los segundos de modo lento",
|
||||
type: ApplicationCommandOptionType.Number,
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: "razon",
|
||||
description: "La razón del modo lento",
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
}
|
||||
],
|
||||
//alias : [],
|
||||
execute: async (ctx, options) => {
|
||||
try {
|
||||
const seconds = options[1].getNumber("segundos", true);
|
||||
const reason = options[1].getString("razon", true);
|
||||
|
||||
(ctx.channel as TextChannel).setRateLimitPerUser(seconds, reason)
|
||||
|
||||
ctx.reply({content: `Se han añadido ${seconds} segundos de modo lento al canal de voz actual`})
|
||||
const sendToMods = ctx.client.guilds.cache.get(process.env.GUILDID!)!.channels.cache.get(process.env.MODLOGS_CHANNEL!) as TextChannel
|
||||
await sendToMods.send({content: `Se ha aplicado modo lento al canal ${ctx.channel}.\nEfectuado por ${ctx.user} con ${seconds} segundos de retardo.\nRazón: ${reason}`})
|
||||
} catch {
|
||||
ctx.reply({content: `No se ha podido aplicar modo lento al canal.`})
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,50 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";
|
||||
import { ApplicationCommandOptionType, GuildMember, TextChannel } from "discord.js";
|
||||
/*
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
*/
|
||||
|
||||
export default commandModule({
|
||||
name: 'timeout',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish(), ownerOnly()],
|
||||
description: 'ADMIN: Silencia a usuarios.',
|
||||
options: [
|
||||
{
|
||||
name: "usuario",
|
||||
description: "Escribe el usuario que silenciar.",
|
||||
type: ApplicationCommandOptionType.User,
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: "razon",
|
||||
description: "Escribe el razon que vas a silenciar.",
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: "minutos",
|
||||
description: "Escribe los minutos que estará silenciado.",
|
||||
type: ApplicationCommandOptionType.Number,
|
||||
min_value: 0,
|
||||
required: true
|
||||
}
|
||||
],
|
||||
//alias : [],
|
||||
execute: async (ctx, options) => {
|
||||
try {
|
||||
const usuario = options[1].getMember('usuario') as GuildMember
|
||||
const minutos = options[1].getNumber('minutos') as number
|
||||
const razon = options[1].getString('razon', true);
|
||||
const minutosToMilisegundos = minutos * 60 * 1000
|
||||
usuario.timeout(minutosToMilisegundos, razon).then(() => {ctx.reply({content: `Se ha silenciado a ${usuario} correctamente.`, ephemeral: true})})
|
||||
const sendToMods = ctx.client.guilds.cache.get(process.env.GUILDID!)!.channels.cache.get(process.env.MODLOGS_CHANNEL!) as TextChannel
|
||||
await sendToMods.send({content: `Se ha silenciado a ${usuario}.\nSlencio efectuado por ${ctx.user} con ${minutos} minutos de duración.\nRazón: ${razon}`})
|
||||
} catch {
|
||||
await ctx.reply({content: `ERROR: No puedo hacer este comando porque a lo mejor soy inferior que el rol de esa persona o estoy usándolo contra admins.`})
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,212 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins";;
|
||||
import { ActionRowBuilder, ApplicationCommandOptionType, ButtonBuilder, ButtonInteraction, ButtonStyle, ComponentType, EmbedBuilder, GuildMember } from "discord.js";
|
||||
import db from '../../schemas/warn.js';
|
||||
|
||||
export default commandModule({
|
||||
name: 'warn',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish(), ownerOnly()],
|
||||
description: 'ADMIN: Avisa a usuarios.',
|
||||
//alias : [],
|
||||
options: [
|
||||
{
|
||||
name: 'leve',
|
||||
description: 'Aviso leve.',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'usuario',
|
||||
description: 'el usuario al que avisar.',
|
||||
type: ApplicationCommandOptionType.User,
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: 'razon',
|
||||
description: 'la razón aviso.',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
name: 'grave',
|
||||
description: 'Aviso grave.',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'usuario',
|
||||
description: 'el usuario al que avisar.',
|
||||
type: ApplicationCommandOptionType.User,
|
||||
required: true
|
||||
},
|
||||
{
|
||||
name: 'razon',
|
||||
description: 'la razón del aviso.',
|
||||
type: ApplicationCommandOptionType.String,
|
||||
required: true
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
name: 'clear',
|
||||
description: 'Elimina los avisos de una persona.',
|
||||
type: ApplicationCommandOptionType.Subcommand,
|
||||
options: [
|
||||
{
|
||||
name: 'usuario',
|
||||
description: 'el usuario al que quitar el aviso.',
|
||||
type: ApplicationCommandOptionType.User,
|
||||
required: true
|
||||
}
|
||||
]
|
||||
}
|
||||
],
|
||||
execute: async (ctx, options) => {
|
||||
const subcommand = options[1].getSubcommand()
|
||||
const user = (options[1].getMember('usuario') as GuildMember).id
|
||||
const usermember = options[1].getMember('usuario') as GuildMember
|
||||
const reason = options[1].getString('razon', true) as string
|
||||
const times = await db.findOne({id: `${user}`}) as any
|
||||
const buttons = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setCustomId('1hour')
|
||||
.setLabel('1 hora')
|
||||
.setStyle(ButtonStyle.Danger),
|
||||
new ButtonBuilder()
|
||||
.setCustomId('30mins')
|
||||
.setLabel('30 minutos')
|
||||
.setStyle(ButtonStyle.Danger),
|
||||
new ButtonBuilder()
|
||||
.setCustomId('15mins')
|
||||
.setLabel('15 minutos')
|
||||
.setStyle(ButtonStyle.Danger),
|
||||
new ButtonBuilder()
|
||||
.setCustomId('pardon')
|
||||
.setLabel('Perdonar')
|
||||
.setStyle(ButtonStyle.Primary)
|
||||
);
|
||||
const dmEmbed = new EmbedBuilder()
|
||||
.setAuthor({name: `${ctx.user.username}`, iconURL: `${ctx.user.displayAvatarURL()}`})
|
||||
.setColor('Red')
|
||||
.setTitle('Tienes un aviso.')
|
||||
.setDescription(`Has sido avisado en el servidor de Discord.\nRazón: ${reason}.`)
|
||||
const dmEmbedTimeout = new EmbedBuilder()
|
||||
.setAuthor({name: `${ctx.user.username}`, iconURL: `${ctx.user.displayAvatarURL()}`})
|
||||
.setColor('Red')
|
||||
.setTitle('Acabas de ser muteado del servidor.')
|
||||
.setDescription(`Ve al servidor de Discord para ver el tiempo que estarás bloqueado.\nRazón: ${reason}.\n**Puede durar hasta una hora.**`)
|
||||
|
||||
switch (subcommand) {
|
||||
case "leve": {
|
||||
return db.exists({id: `${user}`}, async function (err, doc) {
|
||||
if (err) {
|
||||
console.log(err)
|
||||
} else {
|
||||
if (doc === null) {
|
||||
const warn = new db({id: `${user}`, times: 1})
|
||||
warn.save()
|
||||
ctx.reply({content: `Se ha avisado a ${usermember} correctamente y añadido a la base de datos.`, ephemeral: true})
|
||||
ctx.client.users.fetch(user).then((user) => {
|
||||
user.send({embeds: [dmEmbed]})
|
||||
}).catch(() => console.log(`couldn't send a DM to user ID ${user}.`));
|
||||
} else {
|
||||
if (times.times > 2) {
|
||||
const msg = await ctx.reply({content: `El usuario ha excedido 3 avisos, ¿qué hacer?`, ephemeral: true, components: [buttons]})
|
||||
const collector = msg.createMessageComponentCollector({ time: 15000, max: 1, componentType: ComponentType.Button });
|
||||
collector.on('collect', async (i) => {
|
||||
await i.deferReply({ephemeral: true})
|
||||
if (i.customId === '1hour') {
|
||||
await i.editReply({content: `Se ha silenciado a ${usermember} durante 1 hora correctamente. ;-;`})
|
||||
usermember.timeout(60 * 60 * 1000, reason)
|
||||
times.times = 0
|
||||
times.save()
|
||||
} else if (i.customId === '30mins') {
|
||||
await i.editReply({content: `Se ha silenciado a ${usermember} durante 30 minutos correctamente. ;-;`})
|
||||
usermember.timeout(30 * 60 * 1000, reason)
|
||||
times.times = 0
|
||||
times.save()
|
||||
} else if (i.customId === '15mins') {
|
||||
await i.editReply({content: `Se ha silenciado a ${usermember} durante 15 minutos correctamente. ;-;`})
|
||||
usermember.timeout(15 * 60 * 1000, reason)
|
||||
times.times = 0
|
||||
times.save()
|
||||
} else if (i.customId === 'pardon') {
|
||||
await i.editReply({content: `Se ha perdonado a ${usermember} correctamente.\nSeguro que la persona te lo agradecerá! :'D`})
|
||||
times.times = 0
|
||||
times.save()
|
||||
}
|
||||
ctx.client.users.fetch(user).then((user) => {
|
||||
user.send({embeds: [dmEmbedTimeout]})
|
||||
}).catch(() => console.log(`couldn't send a DM to user ID ${user}.`));
|
||||
});
|
||||
} else {
|
||||
ctx.reply({content: `se ha añadido un aviso con el motivo ${reason}.\navisos que tiene ahora: ${times.times + 1}`, ephemeral: true})
|
||||
times.times = times.times + 1
|
||||
times.save()
|
||||
ctx.client.users.fetch(user).then((user) => {
|
||||
user.send({embeds: [dmEmbed]});
|
||||
}).catch(() => console.log(`couldn't send a DM to user ID ${user}.`))
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
case "grave": {
|
||||
return db.exists({id: `${user}`}, async function (err, doc) {
|
||||
if (err) {
|
||||
console.log(err)
|
||||
} else {
|
||||
if (doc === null) {
|
||||
const warn = new db({id: `${user}`, times: 2})
|
||||
warn.save()
|
||||
ctx.reply({content: `Se ha avisado a ${usermember} correctamente y añadido a la base de datos.`, ephemeral: true})
|
||||
ctx.client.users.fetch(user).then((user) => {
|
||||
user.send({embeds: [dmEmbed]});
|
||||
}).catch(() => console.log(`couldn't send a DM to user ID ${user}.`))
|
||||
} else {
|
||||
if (times.times >= 4) {
|
||||
const msg = await ctx.reply({content: `El usuario ha excedido 3 avisos, ¿qué hacer?`, ephemeral: true, components: [buttons]})
|
||||
const collector = msg.createMessageComponentCollector({ time: 1000, max: 1, componentType: ComponentType.Button });
|
||||
collector.on('collect', async (i: any) => {
|
||||
if (i.customId === '1hour') {
|
||||
await i.channel!.send({content: `Se ha silenciado a ${usermember} durante 1 hora correctamente. ;-;`})
|
||||
usermember.timeout(60 * 60 * 1000, reason)
|
||||
times.times = 0
|
||||
times.save()
|
||||
} else if (i.customId === '30mins') {
|
||||
await i.channel!.send({content: `Se ha silenciado a ${usermember} durante 30 minutos correctamente. ;-;`})
|
||||
usermember.timeout(30 * 60 * 1000, reason)
|
||||
times.times = 0
|
||||
times.save()
|
||||
} else if (i.customId === '15mins') {
|
||||
await i.channel!.send({content: `Se ha silenciado a ${usermember} durante 15 minutos correctamente. ;-;`})
|
||||
usermember.timeout(15 * 60 * 1000, reason)
|
||||
times.times = 0
|
||||
times.save()
|
||||
} else if (i.customId === 'pardon') {
|
||||
await i.channel!.send({content: `Se ha perdonado a ${usermember} correctamente.\nSeguro que la persona te lo agradecerá! :'D`})
|
||||
times.times = 0
|
||||
times.save()
|
||||
}
|
||||
ctx.client.users.fetch(user).then((user) => {
|
||||
user.send({embeds: [dmEmbedTimeout]})
|
||||
}).catch(() => console.log(`couldn't send a DM to user ID ${user}.`));
|
||||
});
|
||||
} else {
|
||||
ctx.reply({content: `se ha añadido un aviso con el motivo ${reason}.\navisos que tiene ahora: ${times.times + 2}`, ephemeral: true})
|
||||
times.times = times.times + 2
|
||||
times.save()
|
||||
ctx.client.users.fetch(user).then((user) => {
|
||||
user.send({embeds: [dmEmbed]});
|
||||
}).catch(() => console.log(`couldn't send a DM to user ID ${user}.`))
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
@@ -1,15 +0,0 @@
|
||||
import { commandModule, CommandType } from '@sern/handler'
|
||||
import { publish } from "#plugins";
|
||||
import { ownerOnly } from "#plugins"
|
||||
|
||||
export default commandModule({
|
||||
name: 'ping',
|
||||
type: CommandType.Slash,
|
||||
plugins: [publish()],
|
||||
description: 'A ping command',
|
||||
//alias : [],
|
||||
options: [],
|
||||
execute: async (ctx, options) => {
|
||||
await ctx.reply('Hello World!');
|
||||
},
|
||||
});
|
||||
10
dependencies.d.ts
vendored
10
dependencies.d.ts
vendored
@@ -1,10 +0,0 @@
|
||||
import { SernEmitter, Logging, CoreModuleStore, ModuleManager, ErrorHandling, CoreDependencies, Singleton } from '@sern/handler'
|
||||
import { Client } from 'discord.js'
|
||||
|
||||
declare global {
|
||||
interface Dependencies extends CoreDependencies {
|
||||
'@sern/client': Singleton<Client>
|
||||
}
|
||||
}
|
||||
|
||||
export {}
|
||||
10
deploy.sh
10
deploy.sh
@@ -1,10 +0,0 @@
|
||||
#!/bin/bash
|
||||
git pull
|
||||
|
||||
docker build . -t srizan10/vinci
|
||||
|
||||
docker stop vinci
|
||||
|
||||
docker rm vinci
|
||||
|
||||
docker run -d -t --name vinci -p 7272:7272 --restart unless-stopped srizan10/vinci
|
||||
@@ -1,25 +0,0 @@
|
||||
import { EventType, eventModule } from '@sern/handler';
|
||||
import { EmbedBuilder, Message } from 'discord.js';
|
||||
import db from '../schemas/afk.js';
|
||||
|
||||
export default eventModule({
|
||||
type: EventType.Discord,
|
||||
name: 'messageCreate',
|
||||
execute: async (message: Message) => {
|
||||
const dbEntries = await db.find()
|
||||
|
||||
dbEntries.forEach(async (doc) => {
|
||||
if (!message.content.includes(`<@${doc.id}`)) return;
|
||||
if (message.author.bot) return;
|
||||
const username = (await message.client.users.fetch(doc.id)).username
|
||||
const embed = new EmbedBuilder()
|
||||
.setColor('Red')
|
||||
.setTitle(`Usuario ${username} está AFK`)
|
||||
.setDescription(`El usuario que has mencionado en tu mensaje ha marcado su estado como AFK\nRazón: ${doc.reason}`)
|
||||
.setFooter({ text: 'Este mensaje se eliminará en 10 segundos (wepa, como una bomba!)' })
|
||||
|
||||
const sentMessage = await message.reply({ embeds: [embed] })
|
||||
setTimeout(async () => { await sentMessage.delete() }, 10_000)
|
||||
})
|
||||
},
|
||||
});
|
||||
@@ -1,62 +0,0 @@
|
||||
import { discordEvent } from '@sern/handler';
|
||||
import { ActionRowBuilder, ButtonBuilder, ButtonStyle, EmbedBuilder, Message, TextChannel } from 'discord.js';
|
||||
import tf from '@tensorflow/tfjs-node'
|
||||
import axios from 'axios';
|
||||
import { nsfwModel } from '../index.js';
|
||||
|
||||
export default discordEvent({
|
||||
name: 'messageCreate',
|
||||
execute(message: Message) {
|
||||
message.attachments.forEach(async (attachment) => {
|
||||
switch (attachment.contentType) {
|
||||
case 'image/png':
|
||||
break;
|
||||
case 'image/jpeg':
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
const pic = await axios.get(attachment.url,
|
||||
{ responseType: 'arraybuffer' }
|
||||
)
|
||||
const image = tf.node.decodeImage(pic.data, 3) as tf.Tensor3D
|
||||
// @ts-ignore
|
||||
const predictions = await nsfwModel.classify(image)
|
||||
|
||||
switch (predictions[0].className) {
|
||||
case 'Hentai':
|
||||
case 'Porn':
|
||||
if (predictions[0].probability > 0.75) {
|
||||
const embed = new EmbedBuilder()
|
||||
.setTitle(`Se ha detectado una imagen NSFW en tus adjuntos.`)
|
||||
.setDescription('Por eso, se ha eliminado tu mensaje.\nPor si es un falso positivo, te vamos a dejar abajo el contenido del mensaje para recuperarlo.')
|
||||
.setFields(
|
||||
{ name: 'Contenido del mensaje', value: message.content || '(nada)' },
|
||||
{ name: 'Tipo', value: predictions[0].className.toString() },
|
||||
)
|
||||
.setFooter({ text: 'Esta detección ha sido automatizada.' })
|
||||
const modLogsEmbed = new EmbedBuilder()
|
||||
.setAuthor({ name: message.author.username, iconURL: message.author.displayAvatarURL() })
|
||||
.setTitle(`Se ha detectado una imagen NSFW en los adjuntos de un mensaje.`)
|
||||
.setDescription('Aquí está toda la información:')
|
||||
.setFields(
|
||||
{ name: 'Contenido del mensaje', value: message.content || '(nada)' },
|
||||
{ name: 'Tipo', value: predictions[0].className.toString() },
|
||||
)
|
||||
.setFooter({ text: 'Esta detección ha sido automatizada.' })
|
||||
const button = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setLabel('Imagen adjuntada que saltó las alarmas')
|
||||
.setURL(attachment.url)
|
||||
.setStyle(ButtonStyle.Link)
|
||||
)
|
||||
await message.delete()
|
||||
await message.author.send({ embeds: [embed], components: [button] })
|
||||
await (await message.client.channels.fetch(process.env.MODLOGS_CHANNEL!) as TextChannel).send({ embeds: [modLogsEmbed], components: [button] })
|
||||
}
|
||||
break;
|
||||
}
|
||||
})
|
||||
},
|
||||
});
|
||||
@@ -1,41 +0,0 @@
|
||||
import { discordEvent } from '@sern/handler';
|
||||
import axios from 'axios';
|
||||
import { TextChannel } from 'discord.js';
|
||||
import db from '../schemas/chatgpt.js';
|
||||
|
||||
export default discordEvent({
|
||||
name: 'messageCreate',
|
||||
async execute(message) {
|
||||
if (message.channel.id !== process.env.CHATGPT_CHANNEL) return;
|
||||
if (message.author.bot) return;
|
||||
if (message.content.includes('ig')) return;
|
||||
|
||||
try {
|
||||
await (message.channel as TextChannel).sendTyping()
|
||||
const response = await axios.post('https://chatgpt-api.shn.hk/v1/', {
|
||||
"model": "gpt-3.5-turbo",
|
||||
"messages": [{ "role": "user", "content": message.content }]
|
||||
}).then(res => res.data)
|
||||
const titleResponse = await axios.post('https://chatgpt-api.shn.hk/v1/', {
|
||||
"model": "gpt-3.5-turbo",
|
||||
"messages": [{ "role": "user", "content": `Generate a title in less than 6 words for the following message, also remove the quotes if you are going to add them AND don't put Title in the beginning:\nUser: ${message.content}\nAssistant: ${response.choices[0].message.content}` }]
|
||||
}).then(res => res.data.choices[0].message.content.replaceAll('"', '') as string)
|
||||
|
||||
const botMsg = await message.reply({ content: response.choices[0].message.content.slice(0, 2000) })
|
||||
const thread = await botMsg.startThread({ name: titleResponse })
|
||||
|
||||
const dbData = new db({
|
||||
messageid: message.id,
|
||||
threadid: thread.id,
|
||||
messages: [
|
||||
{ role: 'user', content: message.content },
|
||||
{ role: 'assistant', content: response.choices[0].message.content.replace(/^\n{2}/, '') }
|
||||
]
|
||||
})
|
||||
await dbData.save()
|
||||
} catch (e) {
|
||||
await message.reply({ content: 'Algo ha ido mal.' }).catch(() => {})
|
||||
console.log(e)
|
||||
}
|
||||
},
|
||||
});
|
||||
@@ -1,53 +0,0 @@
|
||||
import { discordEvent } from '@sern/handler';
|
||||
import axios from 'axios';
|
||||
import { ThreadChannel } from 'discord.js';
|
||||
import database from '../schemas/chatgpt.js';
|
||||
|
||||
export default discordEvent({
|
||||
name: 'messageCreate',
|
||||
async execute(message) {
|
||||
const thread = message.channel as ThreadChannel
|
||||
if (thread.parentId !== process.env.CHATGPT_CHANNEL) return;
|
||||
if (message.author.bot) return;
|
||||
if (message.content.includes('ig')) return;
|
||||
|
||||
try {
|
||||
await thread.sendTyping()
|
||||
let newObj = { role: 'user', content: message.content }
|
||||
let db = await database.findOneAndUpdate({ threadid: thread.id }, {
|
||||
$push: {
|
||||
messages: newObj
|
||||
}
|
||||
})
|
||||
const messages = db!.messages.map((message) => {
|
||||
const { _id, ...rest } = message.toObject(); // Convert Mongoose document to plain object and remove _id field
|
||||
return rest
|
||||
})
|
||||
|
||||
const response = await axios.post('https://chatgpt-api.shn.hk/v1/', {
|
||||
"model": "gpt-3.5-turbo",
|
||||
"messages": messages
|
||||
}, {
|
||||
headers: {
|
||||
'Content-Type': 'application/json'
|
||||
}
|
||||
}).then(res => res.data.choices[0].message.content as string)
|
||||
|
||||
newObj = { role: 'assistant', content: response }
|
||||
db = await database.findOneAndUpdate({ threadid: thread.id }, {
|
||||
$push: {
|
||||
messages: newObj
|
||||
}
|
||||
})
|
||||
|
||||
await message.reply({ content: response.slice(0, 2000) })
|
||||
} catch (e) {
|
||||
await message.reply('Algo ha ido mal.')
|
||||
console.log(e)
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
function replacer(key, value) {
|
||||
return value.replace(/[^\w\s]/gi, '');
|
||||
}
|
||||
@@ -1,9 +0,0 @@
|
||||
import { EventType, eventModule } from "@sern/handler";
|
||||
|
||||
export default eventModule({
|
||||
type: EventType.Sern,
|
||||
name : 'error',
|
||||
execute(err) {
|
||||
console.log(err);
|
||||
}
|
||||
})
|
||||
@@ -1,20 +0,0 @@
|
||||
import { EmbedBuilder, GuildMember, TextChannel } from "discord.js";
|
||||
|
||||
import { EventType, eventModule } from "@sern/handler";
|
||||
|
||||
export default eventModule({
|
||||
type: EventType.Discord,
|
||||
name: 'guildMemberAdd',
|
||||
execute(member: GuildMember) {
|
||||
if (member.guild.id !== process.env.GUILDID) return;
|
||||
const newMemberEmbed = new EmbedBuilder()
|
||||
.setColor("Random")
|
||||
.setTitle("Nuevo miembro!")
|
||||
.setDescription(`${member.user} acaba de entrar al servidor!`)
|
||||
.setThumbnail(member.user.displayAvatarURL())
|
||||
.setTimestamp();
|
||||
|
||||
const channel = member.client.guilds.cache.get(process.env.GUILDID!)!.channels.cache.get(process.env.JOINSANDLEAVES_CHANNEL!) as TextChannel
|
||||
channel.send({embeds: [newMemberEmbed]})
|
||||
}
|
||||
});
|
||||
@@ -1,20 +0,0 @@
|
||||
import { EmbedBuilder, GuildMember, TextChannel } from "discord.js";
|
||||
|
||||
import { EventType, eventModule } from "@sern/handler";
|
||||
|
||||
export default eventModule({
|
||||
type: EventType.Discord,
|
||||
name: 'guildMemberRemove',
|
||||
execute(member: GuildMember) {
|
||||
if (member.guild.id !== process.env.GUILDID) return;
|
||||
const leaveEmbed = new EmbedBuilder()
|
||||
.setColor("Random")
|
||||
.setTitle("Un miembro se ha ido :(")
|
||||
.setDescription(`${member.user} acaba de salir del servidor!`)
|
||||
.setThumbnail(member.user.displayAvatarURL())
|
||||
.setTimestamp();
|
||||
|
||||
const channel = member.client.guilds.cache.get(process.env.GUILDID!)!.channels.cache.get(process.env.JOINSANDLEAVES_CHANNEL!) as TextChannel
|
||||
channel.send({embeds: [leaveEmbed]})
|
||||
}
|
||||
});
|
||||
@@ -1,53 +0,0 @@
|
||||
import { discordEvent } from '@sern/handler';
|
||||
import {
|
||||
ActionRowBuilder,
|
||||
ButtonBuilder,
|
||||
ButtonStyle,
|
||||
EmbedBuilder,
|
||||
TextChannel,
|
||||
} from 'discord.js';
|
||||
import { scamLinks } from '../index.js';
|
||||
|
||||
export default discordEvent({
|
||||
name: 'messageCreate',
|
||||
async execute(message) {
|
||||
if (!message.content.includes('https://')) return;
|
||||
|
||||
const index = message.content.indexOf("https://");
|
||||
let link = 'some goofy ahh string that is gonna be replaced'
|
||||
if (index !== -1) {
|
||||
let endIndex = message.content.indexOf(" ", index);
|
||||
if (endIndex === -1) {
|
||||
endIndex = message.content.length;
|
||||
}
|
||||
link = message.content.substring(index, endIndex);
|
||||
}
|
||||
const url = new URL(link);
|
||||
if (scamLinks.includes(url.hostname)) {
|
||||
const embed = new EmbedBuilder()
|
||||
.setTitle(`Se ha detectado un enlace scam en tu mensaje.`)
|
||||
.setDescription('Por eso, se ha eliminado tu mensaje.\nPor si es un falso positivo, te vamos a dejar abajo el contenido del mensaje para recuperarlo.')
|
||||
.setFields(
|
||||
{ name: 'Contenido del mensaje', value: message.content || '(nada)' },
|
||||
)
|
||||
.setFooter({ text: 'Esta detección ha sido automatizada por Vinci.' })
|
||||
const modLogsEmbed = new EmbedBuilder()
|
||||
.setTitle(`Se ha detectado un enlace scam el mensaje de un usuario.`)
|
||||
.setDescription('Por eso, se ha eliminado el mensaje.')
|
||||
.setFields(
|
||||
{ name: 'Contenido del mensaje', value: message.content || '(nada)' },
|
||||
)
|
||||
.setFooter({ text: 'Esta detección ha sido automatizada por Vinci.' })
|
||||
const button = new ActionRowBuilder<ButtonBuilder>()
|
||||
.addComponents(
|
||||
new ButtonBuilder()
|
||||
.setLabel('Enlace que saltó las alarmas.')
|
||||
.setURL(link)
|
||||
.setStyle(ButtonStyle.Link)
|
||||
)
|
||||
await message.delete()
|
||||
await message.author.send({ embeds: [embed], components: [button] })
|
||||
await (await message.client.channels.fetch(process.env.MODLOGS_CHANNEL!) as TextChannel).send({ embeds: [modLogsEmbed], components: [button] })
|
||||
}
|
||||
},
|
||||
});
|
||||
90
index.ts
90
index.ts
@@ -1,90 +0,0 @@
|
||||
import { DefaultLogging, makeDependencies, single, Singleton } from '@sern/handler';
|
||||
import { ActivityOptions, ActivityType } from 'discord.js';
|
||||
import { Client, GatewayIntentBits } from 'discord.js';
|
||||
import { Sern } from '@sern/handler';
|
||||
import { config as dotenv } from 'dotenv';
|
||||
import mongoose from 'mongoose';
|
||||
import youtubenotifications from './util/youtubenotifications.js';
|
||||
import { setIntervalAsync } from 'set-interval-async';
|
||||
import birthdays from './util/birthdays.js';
|
||||
import minecraftstatus from './util/minecraftstatus.js';
|
||||
import axios from 'axios';
|
||||
// import giveawaychecker from './util/giveawaychecker.js';
|
||||
|
||||
let devMode: boolean
|
||||
if (process.argv[2] === '--dev') {
|
||||
devMode = true
|
||||
dotenv({path: '.env.dev'})
|
||||
console.clear()
|
||||
} else {
|
||||
dotenv()
|
||||
}
|
||||
|
||||
const client = new Client({
|
||||
intents: [
|
||||
GatewayIntentBits.Guilds,
|
||||
GatewayIntentBits.GuildMessages,
|
||||
GatewayIntentBits.GuildMembers,
|
||||
GatewayIntentBits.MessageContent,
|
||||
GatewayIntentBits.GuildMembers,
|
||||
GatewayIntentBits.GuildMessageReactions,
|
||||
GatewayIntentBits.GuildVoiceStates,
|
||||
],
|
||||
});
|
||||
|
||||
mongoose.connect(process.env.MONGODB!).then(() => {
|
||||
console.log('Connected to MongoDB');
|
||||
});
|
||||
|
||||
interface MyDependencies extends Dependencies {
|
||||
'@sern/client' : Singleton<Client>;
|
||||
'@sern/logger' : Singleton<DefaultLogging>
|
||||
}
|
||||
|
||||
await makeDependencies<MyDependencies>({
|
||||
build: (root) => root.add({ '@sern/client': single(() => client) }),
|
||||
});
|
||||
|
||||
Sern.init({
|
||||
commands: 'dist/commands',
|
||||
events: 'dist/events',
|
||||
defaultPrefix: process.env.PREFIX,
|
||||
});
|
||||
|
||||
client.on('ready', async () => {
|
||||
console.log('Logged on!');
|
||||
|
||||
setInterval(() => {
|
||||
const statuses = [
|
||||
{ name: 'Minecraft', type: ActivityType.Playing },
|
||||
{ name: 'cómo escribe Javi', type: ActivityType.Watching },
|
||||
{ name: 'quinto libro when', type: ActivityType.Watching },
|
||||
{ name: 'a Hermes', type: ActivityType.Watching },
|
||||
{ name: 'tus comandos', type: ActivityType.Listening },
|
||||
{ name: 'tu voz', type: ActivityType.Listening },
|
||||
{ name: 'ahora v1.0!', type: ActivityType.Playing },
|
||||
] as ActivityOptions[];
|
||||
const randomStatus = statuses[Math.floor(Math.random() * statuses.length)];
|
||||
client.user.setActivity(randomStatus);
|
||||
}, 10000);
|
||||
|
||||
if (!devMode) {
|
||||
setIntervalAsync(async () => {
|
||||
await youtubenotifications(client);
|
||||
}, 120_000);
|
||||
|
||||
setIntervalAsync(async () => {
|
||||
await birthdays(client);
|
||||
}, 3_600_000);
|
||||
|
||||
setIntervalAsync(async () => {
|
||||
await minecraftstatus(client);
|
||||
}, 20_000);
|
||||
} else {
|
||||
console.log('DevMode got activated, there are no checkers in this version.')
|
||||
}
|
||||
});
|
||||
|
||||
export const scamLinks = await axios.get('https://api.hyperphish.com/gimme-domains').then(res => res.data as Array<string>)
|
||||
|
||||
client.login(process.env.TOKEN);
|
||||
1
nixpacks.toml
Normal file
1
nixpacks.toml
Normal file
@@ -0,0 +1 @@
|
||||
providers = ["node", "python"]
|
||||
106
package.json
106
package.json
@@ -1,66 +1,44 @@
|
||||
{
|
||||
"name": "vinci",
|
||||
"version": "1.0.0",
|
||||
"description": "Vinci Discord Bot for Mara Turing",
|
||||
"main": "dist/index.js",
|
||||
"scripts": {
|
||||
"test": "echo \"Error: no test specified\" && exit 1",
|
||||
"dev": "tsc-watch -p \"./tsconfig.json\" --onSuccess \"node ./dist/index.js --dev\"",
|
||||
"compile": "tsc --build",
|
||||
"build": "tsc --build",
|
||||
"web": "node webserver.js",
|
||||
"watch": "tsc --watch",
|
||||
"start": "nodemon dist/index.js"
|
||||
},
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "git+https://github.com/SrIzan10/vinci.git"
|
||||
},
|
||||
"imports": {
|
||||
"#plugins": [
|
||||
"./dist/plugins/index.js"
|
||||
]
|
||||
},
|
||||
"keywords": [
|
||||
"discord-bot"
|
||||
],
|
||||
"type": "module",
|
||||
"author": "Sr Izan",
|
||||
"license": "MIT",
|
||||
"bugs": {
|
||||
"url": "https://github.com/SrIzan10/vinci/issues"
|
||||
},
|
||||
"homepage": "https://github.com/SrIzan10/vinci#readme",
|
||||
"dependencies": {
|
||||
"@consumet/extensions": "1.3.5",
|
||||
"@discordjs/opus": "^0.9.0",
|
||||
"@discordjs/voice": "^0.15.0",
|
||||
"@napi-rs/canvas": "^0.1.30",
|
||||
"@sern/handler": "^3.0.3",
|
||||
"axios": "^1.1.3",
|
||||
"dayjs": "^1.11.6",
|
||||
"discord-tictactoe": "^4.0.0",
|
||||
"discord.js": "^14.13.0",
|
||||
"dotenv": "^16.0.1",
|
||||
"execa": "^6.1.0",
|
||||
"express": "^4.18.1",
|
||||
"form-data": "^4.0.0",
|
||||
"genius-lyrics": "^4.4.3",
|
||||
"googlethis": "^1.7.1",
|
||||
"got": "^12.5.3",
|
||||
"libsodium-wrappers": "^0.7.10",
|
||||
"mongoose": "^6.11.3",
|
||||
"node-fetch": "^3.3.1",
|
||||
"pretty-seconds-spanish": "^2.1.1",
|
||||
"rockpaperscissors-checker": "^1.2.0",
|
||||
"set-interval-async": "^3.0.2",
|
||||
"stringify-safe": "^1.0.3",
|
||||
"systeminformation": "^5.12.6"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/express": "^4.17.14",
|
||||
"ts-node": "10.9.1",
|
||||
"tsc-watch": "^5.0.3",
|
||||
"typescript": "^5.2.2"
|
||||
}
|
||||
"name": "ts-example",
|
||||
"version": "1.0.0",
|
||||
"private": true,
|
||||
"description": "",
|
||||
"main": "dist/index.js",
|
||||
"scripts": {
|
||||
"build": "sern build",
|
||||
"start": "bun run --inspect .",
|
||||
"db:migrate": "prisma migrate deploy",
|
||||
"install": "sern build",
|
||||
"commands:publish": "sern commands publish",
|
||||
"dev": "sern build -w --watch-command \"bun start\"",
|
||||
"db:mongo": "bun run src/utils/db/migrateMongo.ts"
|
||||
},
|
||||
"keywords": [
|
||||
"typescript",
|
||||
"sern",
|
||||
"discord.js"
|
||||
],
|
||||
"dependencies": {
|
||||
"@napi-rs/canvas": "^0.1.72",
|
||||
"@prisma/client": "^6.10.1",
|
||||
"@sern/handler": "^4.2.4",
|
||||
"@sern/publisher": "1.1.2",
|
||||
"discord.js": "^14.21.0",
|
||||
"dotenv": "^16.3.1",
|
||||
"execa": "^9.6.0",
|
||||
"mongodb": "^6.17.0",
|
||||
"node-html-parser": "^7.0.1",
|
||||
"openai": "^5.10.2",
|
||||
"rockpaperscissors-checker": "^1.2.0",
|
||||
"sharp": "^0.34.2"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@sern/cli": "^1.4.0",
|
||||
"@types/bun": "^1.2.18",
|
||||
"@types/mongodb": "^4.0.7",
|
||||
"@types/node": "^17.0.25",
|
||||
"prisma": "^6.10.1",
|
||||
"typescript": "^5.0"
|
||||
},
|
||||
"type": "module"
|
||||
}
|
||||
|
||||
@@ -1,107 +0,0 @@
|
||||
//@ts-nocheck
|
||||
/**
|
||||
* This is buttonConfirmation plugin, it runs confirmation prompt in the form of buttons.
|
||||
* Note that you need to use edit/editReply in the command itself because we are already replying in the plugin!
|
||||
* Credits to original plugin of confirmation using reactions and its author!
|
||||
*
|
||||
* @author @EvolutionX-10 [<@697795666373640213>]
|
||||
* @version 1.0.0
|
||||
* @example
|
||||
* ```ts
|
||||
* import { buttonConfirmation } from "../plugins/buttonConfirmation";
|
||||
* import { commandModule } from "@sern/handler";
|
||||
* export default commandModule({
|
||||
* plugins: [ buttonConfirmation() ],
|
||||
* execute: (ctx) => {
|
||||
* //your code here
|
||||
* }
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
|
||||
import { CommandControlPlugin, CommandType, controller } from "@sern/handler";
|
||||
import {
|
||||
ActionRowBuilder,
|
||||
ButtonBuilder,
|
||||
ButtonStyle,
|
||||
ComponentType,
|
||||
} from "discord.js";
|
||||
|
||||
export function acceptingBirthday(options?: Partial<ConfirmationOptions>) {
|
||||
return CommandControlPlugin<CommandType.Both>(async (ctx, args) => {
|
||||
options = {
|
||||
content: "Se va a guardar tu cumpleaños en la base de datos de Vinci.\nAceptas?",
|
||||
denialMessage: "Ok pues...",
|
||||
labels: ["No", "Sí"],
|
||||
time: 60_000,
|
||||
wrongUserResponse: "Esto no es para tí!",
|
||||
...options,
|
||||
};
|
||||
|
||||
const buttons = options.labels!.map((l, i) => {
|
||||
return new ButtonBuilder()
|
||||
.setCustomId(l)
|
||||
.setLabel(l)
|
||||
.setStyle(
|
||||
i === 0 ? ButtonStyle.Danger : ButtonStyle.Success
|
||||
);
|
||||
});
|
||||
const sent = await ctx.reply({
|
||||
content: options.content,
|
||||
components: [
|
||||
new ActionRowBuilder<ButtonBuilder>().setComponents(
|
||||
buttons
|
||||
),
|
||||
],
|
||||
ephemeral: true
|
||||
});
|
||||
|
||||
const collector = sent.createMessageComponentCollector({
|
||||
componentType: ComponentType.Button,
|
||||
filter: (i) => i.user.id === ctx.user.id,
|
||||
time: options.time,
|
||||
});
|
||||
|
||||
return new Promise((resolve) => {
|
||||
collector.on("collect", async (i) => {
|
||||
await i.update({ components: [] });
|
||||
collector.stop();
|
||||
if (i.customId === options!.labels![1]) {
|
||||
resolve(controller.next());
|
||||
return;
|
||||
}
|
||||
await i.editReply({
|
||||
content: options?.denialMessage,
|
||||
});
|
||||
resolve(controller.stop());
|
||||
});
|
||||
|
||||
collector.on("end", async (c) => {
|
||||
if (c.size) return;
|
||||
buttons.forEach((b) => b.setDisabled());
|
||||
await sent.edit({
|
||||
components: [
|
||||
new ActionRowBuilder<ButtonBuilder>().setComponents(
|
||||
buttons
|
||||
),
|
||||
],
|
||||
});
|
||||
});
|
||||
|
||||
collector.on("ignore", async (i) => {
|
||||
await i.reply({
|
||||
content: options?.wrongUserResponse,
|
||||
ephemeral: true,
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
interface ConfirmationOptions {
|
||||
content: string;
|
||||
denialMessage: string;
|
||||
time: number;
|
||||
labels: [string, string];
|
||||
wrongUserResponse: string;
|
||||
}
|
||||
@@ -1,4 +0,0 @@
|
||||
export * from './publish.js'
|
||||
export * from './ownerOnly.js'
|
||||
export * from './srIzanOnly.js'
|
||||
export * from './acceptingBirthday.js'
|
||||
@@ -1,29 +0,0 @@
|
||||
// @ts-nocheck
|
||||
/**
|
||||
* This is OwnerOnly plugin, it allows only bot owners to run the command, like eval.
|
||||
*
|
||||
* @author @EvolutionX-10 [<@697795666373640213>]
|
||||
* @version 1.0.0
|
||||
* @example
|
||||
* ```ts
|
||||
* import { ownerOnly } from "../plugins/ownerOnly";
|
||||
* import { commandModule } from "@sern/handler";
|
||||
* export default commandModule({
|
||||
* plugins: [ ownerOnly() ],
|
||||
* execute: (ctx) => {
|
||||
* //your code here
|
||||
* }
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
|
||||
import { CommandType, CommandControlPlugin, controller } from "@sern/handler";
|
||||
const ownerIDs = ["464397024247152640", "703974042700611634", '252679156465139722', '370918560446545922', '375984365181599744', '785836117630910485', '368107342140801025']; //! Fill your ID
|
||||
export function ownerOnly() {
|
||||
return CommandControlPlugin<CommandType.Both>((ctx, args) => {
|
||||
if (ownerIDs.includes(ctx.user.id)) return controller.next();
|
||||
//* If you want to reply when the command fails due to user not being owner, you can use following
|
||||
ctx.reply("**ERROR**: Sólo los administradores pueden correr este comando.");
|
||||
return controller.stop(); //! Important: It stops the execution of command!
|
||||
});
|
||||
}
|
||||
@@ -1,215 +0,0 @@
|
||||
// @ts-nocheck
|
||||
/**
|
||||
* @plugin
|
||||
* [DEPRECATED] It allows you to publish your application commands using the discord.js library with ease.
|
||||
*
|
||||
* @author @EvolutionX-10 [<@697795666373640213>]
|
||||
* @version 2.0.0
|
||||
* @example
|
||||
* ```ts
|
||||
* import { publish } from "../plugins/publish";
|
||||
* import { commandModule } from "@sern/handler";
|
||||
* export default commandModule({
|
||||
* plugins: [ publish() ], // put an object containing permissions, ids for guild commands, boolean for dmPermission
|
||||
* // plugins: [ publish({ guildIds: ['guildId'], defaultMemberPermissions: 'Administrator'})]
|
||||
* execute: (ctx) => {
|
||||
* //your code here
|
||||
* }
|
||||
* })
|
||||
* ```
|
||||
* @end
|
||||
*/
|
||||
import {
|
||||
CommandInitPlugin,
|
||||
CommandType,
|
||||
controller,
|
||||
SernOptionsData,
|
||||
SlashCommand,
|
||||
Service,
|
||||
} from "@sern/handler";
|
||||
import {
|
||||
ApplicationCommandData,
|
||||
ApplicationCommandType,
|
||||
ApplicationCommandOptionType,
|
||||
PermissionResolvable,
|
||||
} from "discord.js";
|
||||
|
||||
export const CommandTypeRaw = {
|
||||
[CommandType.Both]: ApplicationCommandType.ChatInput,
|
||||
[CommandType.CtxUser]: ApplicationCommandType.User,
|
||||
[CommandType.CtxMsg]: ApplicationCommandType.Message,
|
||||
[CommandType.Slash]: ApplicationCommandType.ChatInput,
|
||||
} as const;
|
||||
|
||||
export function publish<
|
||||
T extends
|
||||
| CommandType.Both
|
||||
| CommandType.Slash
|
||||
| CommandType.CtxMsg
|
||||
| CommandType.CtxUser,
|
||||
>(options?: PublishOptions) {
|
||||
return CommandInitPlugin<T>(async ({ module }) => {
|
||||
// Users need to provide their own useContainer function.
|
||||
let client;
|
||||
try {
|
||||
client = (await import("@sern/handler")).Service("@sern/client");
|
||||
} catch {
|
||||
const { useContainer } = await import("../index.js");
|
||||
client = useContainer("@sern/client")[0];
|
||||
}
|
||||
const defaultOptions = {
|
||||
guildIds: [],
|
||||
dmPermission: undefined,
|
||||
defaultMemberPermissions: null,
|
||||
};
|
||||
|
||||
options = { ...defaultOptions, ...options } as PublishOptions &
|
||||
ValidPublishOptions;
|
||||
let { defaultMemberPermissions, dmPermission, guildIds } =
|
||||
options as unknown as ValidPublishOptions;
|
||||
|
||||
function c(e: unknown) {
|
||||
console.error("publish command didnt work for", module.name);
|
||||
console.error(e);
|
||||
}
|
||||
|
||||
const log =
|
||||
(...message: any[]) =>
|
||||
() =>
|
||||
console.log(...message);
|
||||
const logged = (...message: any[]) => log(message);
|
||||
/**
|
||||
* a local function that returns either one value or the other,
|
||||
* depending on {t}'s CommandType. If the commandtype of
|
||||
* this module is CommandType.Both or CommandType.Text or CommandType.Slash,
|
||||
* return 'is', else return 'els'
|
||||
* @param t
|
||||
* @returns S | T
|
||||
*/
|
||||
const appCmd = <V extends CommandType, S, T>(t: V) => {
|
||||
return (is: S, els: T) => ((t & CommandType.Both) !== 0 ? is : els);
|
||||
};
|
||||
const curAppType = CommandTypeRaw[module.type];
|
||||
const createCommandData = () => {
|
||||
const cmd = appCmd(module.type);
|
||||
return {
|
||||
name: module.name,
|
||||
type: curAppType,
|
||||
description: cmd(module.description, ""),
|
||||
options: cmd(
|
||||
optionsTransformer((module as SlashCommand).options ?? []),
|
||||
[],
|
||||
),
|
||||
defaultMemberPermissions,
|
||||
dmPermission,
|
||||
} as ApplicationCommandData;
|
||||
};
|
||||
|
||||
try {
|
||||
const commandData = createCommandData();
|
||||
|
||||
if (!guildIds.length) {
|
||||
const cmd = (await client.application!.commands.fetch()).find(
|
||||
(c) => c.name === module.name && c.type === curAppType,
|
||||
);
|
||||
if (cmd) {
|
||||
if (!cmd.equals(commandData, true)) {
|
||||
logged(
|
||||
`Found differences in global command ${module.name}`,
|
||||
);
|
||||
cmd.edit(commandData).then(
|
||||
log(
|
||||
`${module.name} updated with new data successfully!`,
|
||||
),
|
||||
);
|
||||
}
|
||||
return controller.next();
|
||||
}
|
||||
client
|
||||
.application!.commands.create(commandData)
|
||||
.then(log("Command created", module.name))
|
||||
.catch(c);
|
||||
return controller.next();
|
||||
}
|
||||
|
||||
for (const id of guildIds) {
|
||||
const guild = await client.guilds.fetch(id).catch(c);
|
||||
if (!guild) continue;
|
||||
const guildCmd = (await guild.commands.fetch()).find(
|
||||
(c) => c.name === module.name && c.type === curAppType,
|
||||
);
|
||||
if (guildCmd) {
|
||||
if (!guildCmd.equals(commandData, true)) {
|
||||
logged(`Found differences in command ${module.name}`);
|
||||
guildCmd
|
||||
.edit(commandData)
|
||||
.then(
|
||||
log(
|
||||
`${module.name} updated with new data successfully!`,
|
||||
),
|
||||
)
|
||||
.catch(c);
|
||||
continue;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
guild.commands
|
||||
.create(commandData)
|
||||
.then(log("Guild Command created", module.name, guild.name))
|
||||
.catch(c);
|
||||
}
|
||||
return controller.next();
|
||||
} catch (e) {
|
||||
logged("Command did not register" + module.name);
|
||||
logged(e);
|
||||
return controller.stop();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
export function optionsTransformer(ops: Array<SernOptionsData>) {
|
||||
return ops.map((el) => {
|
||||
switch (el.type) {
|
||||
case ApplicationCommandOptionType.String:
|
||||
case ApplicationCommandOptionType.Number:
|
||||
case ApplicationCommandOptionType.Integer: {
|
||||
return el.autocomplete && "command" in el
|
||||
? (({ command, ...el }) => el)(el)
|
||||
: el;
|
||||
}
|
||||
default:
|
||||
return el;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
export type NonEmptyArray<T extends `${number}` = `${number}`> = [T, ...T[]];
|
||||
|
||||
export interface ValidPublishOptions {
|
||||
guildIds: string[];
|
||||
dmPermission: boolean;
|
||||
defaultMemberPermissions: PermissionResolvable;
|
||||
}
|
||||
|
||||
interface GuildPublishOptions {
|
||||
guildIds?: NonEmptyArray;
|
||||
defaultMemberPermissions?: PermissionResolvable;
|
||||
dmPermission?: never;
|
||||
}
|
||||
|
||||
interface GlobalPublishOptions {
|
||||
defaultMemberPermissions?: PermissionResolvable;
|
||||
dmPermission?: false;
|
||||
guildIds?: never;
|
||||
}
|
||||
|
||||
type BasePublishOptions = GuildPublishOptions | GlobalPublishOptions;
|
||||
|
||||
export type PublishOptions = BasePublishOptions &
|
||||
(
|
||||
| Required<Pick<BasePublishOptions, "defaultMemberPermissions">>
|
||||
| (
|
||||
| Required<Pick<BasePublishOptions, "dmPermission">>
|
||||
| Required<Pick<BasePublishOptions, "guildIds">>
|
||||
)
|
||||
);
|
||||
@@ -1,29 +0,0 @@
|
||||
// @ts-nocheck
|
||||
/**
|
||||
* This is OwnerOnly plugin, it allows only bot owners to run the command, like eval.
|
||||
*
|
||||
* @author @EvolutionX-10 [<@697795666373640213>]
|
||||
* @version 1.0.0
|
||||
* @example
|
||||
* ```ts
|
||||
* import { ownerOnly } from "../plugins/ownerOnly";
|
||||
* import { commandModule } from "@sern/handler";
|
||||
* export default commandModule({
|
||||
* plugins: [ ownerOnly() ],
|
||||
* execute: (ctx) => {
|
||||
* //your code here
|
||||
* }
|
||||
* })
|
||||
* ```
|
||||
*/
|
||||
|
||||
import { CommandType, CommandControlPlugin, controller } from "@sern/handler";
|
||||
const ownerIDs = ['703974042700611634']; //! Fill your ID
|
||||
export function srIzanOnly() {
|
||||
return CommandControlPlugin<CommandType.Both>((ctx, args) => {
|
||||
if (ownerIDs.includes(ctx.user.id)) return controller.next();
|
||||
//* If you want to reply when the command fails due to user not being owner, you can use following
|
||||
ctx.reply("**ERROR**: Sólo Sr Izan puede correr este comando.");
|
||||
return controller.stop(); //! Important: It stops the execution of command!
|
||||
});
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
-- CreateTable
|
||||
CREATE TABLE "ai_chats" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"messageid" TEXT NOT NULL,
|
||||
"threadid" TEXT NOT NULL
|
||||
);
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "AIMessage" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"role" TEXT NOT NULL,
|
||||
"content" TEXT NOT NULL,
|
||||
"aiChatId" INTEGER NOT NULL,
|
||||
CONSTRAINT "AIMessage_aiChatId_fkey" FOREIGN KEY ("aiChatId") REFERENCES "ai_chats" ("id") ON DELETE RESTRICT ON UPDATE CASCADE
|
||||
);
|
||||
19
prisma/migrations/20250628135845_fix_caps/migration.sql
Normal file
19
prisma/migrations/20250628135845_fix_caps/migration.sql
Normal file
@@ -0,0 +1,19 @@
|
||||
/*
|
||||
Warnings:
|
||||
|
||||
- You are about to drop the `AIMessage` table. If the table is not empty, all the data it contains will be lost.
|
||||
|
||||
*/
|
||||
-- DropTable
|
||||
PRAGMA foreign_keys=off;
|
||||
DROP TABLE "AIMessage";
|
||||
PRAGMA foreign_keys=on;
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "AiMessage" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"role" TEXT NOT NULL,
|
||||
"content" TEXT NOT NULL,
|
||||
"aiChatId" INTEGER NOT NULL,
|
||||
CONSTRAINT "AiMessage_aiChatId_fkey" FOREIGN KEY ("aiChatId") REFERENCES "ai_chats" ("id") ON DELETE RESTRICT ON UPDATE CASCADE
|
||||
);
|
||||
@@ -0,0 +1,33 @@
|
||||
/*
|
||||
Warnings:
|
||||
|
||||
- You are about to drop the `ai_chats` table. If the table is not empty, all the data it contains will be lost.
|
||||
|
||||
*/
|
||||
-- DropTable
|
||||
PRAGMA foreign_keys=off;
|
||||
DROP TABLE "ai_chats";
|
||||
PRAGMA foreign_keys=on;
|
||||
|
||||
-- CreateTable
|
||||
CREATE TABLE "AiChat" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"messageid" TEXT NOT NULL,
|
||||
"threadid" TEXT NOT NULL
|
||||
);
|
||||
|
||||
-- RedefineTables
|
||||
PRAGMA defer_foreign_keys=ON;
|
||||
PRAGMA foreign_keys=OFF;
|
||||
CREATE TABLE "new_AiMessage" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"role" TEXT NOT NULL,
|
||||
"content" TEXT NOT NULL,
|
||||
"aiChatId" INTEGER NOT NULL,
|
||||
CONSTRAINT "AiMessage_aiChatId_fkey" FOREIGN KEY ("aiChatId") REFERENCES "AiChat" ("id") ON DELETE RESTRICT ON UPDATE CASCADE
|
||||
);
|
||||
INSERT INTO "new_AiMessage" ("aiChatId", "content", "id", "role") SELECT "aiChatId", "content", "id", "role" FROM "AiMessage";
|
||||
DROP TABLE "AiMessage";
|
||||
ALTER TABLE "new_AiMessage" RENAME TO "AiMessage";
|
||||
PRAGMA foreign_keys=ON;
|
||||
PRAGMA defer_foreign_keys=OFF;
|
||||
10
prisma/migrations/20250628140420_afk/migration.sql
Normal file
10
prisma/migrations/20250628140420_afk/migration.sql
Normal file
@@ -0,0 +1,10 @@
|
||||
-- CreateTable
|
||||
CREATE TABLE "Afk" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"userId" TEXT NOT NULL,
|
||||
"reason" TEXT NOT NULL,
|
||||
"expiresAt" DATETIME NOT NULL
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "Afk_userId_key" ON "Afk"("userId");
|
||||
12
prisma/migrations/20250628140820_unique_chat/migration.sql
Normal file
12
prisma/migrations/20250628140820_unique_chat/migration.sql
Normal file
@@ -0,0 +1,12 @@
|
||||
/*
|
||||
Warnings:
|
||||
|
||||
- A unique constraint covering the columns `[messageid]` on the table `AiChat` will be added. If there are existing duplicate values, this will fail.
|
||||
- A unique constraint covering the columns `[threadid]` on the table `AiChat` will be added. If there are existing duplicate values, this will fail.
|
||||
|
||||
*/
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "AiChat_messageid_key" ON "AiChat"("messageid");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "AiChat_threadid_key" ON "AiChat"("threadid");
|
||||
@@ -0,0 +1,20 @@
|
||||
/*
|
||||
Warnings:
|
||||
|
||||
- You are about to drop the column `expiresAt` on the `Afk` table. All the data in the column will be lost.
|
||||
|
||||
*/
|
||||
-- RedefineTables
|
||||
PRAGMA defer_foreign_keys=ON;
|
||||
PRAGMA foreign_keys=OFF;
|
||||
CREATE TABLE "new_Afk" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"userId" TEXT NOT NULL,
|
||||
"reason" TEXT NOT NULL
|
||||
);
|
||||
INSERT INTO "new_Afk" ("id", "reason", "userId") SELECT "id", "reason", "userId" FROM "Afk";
|
||||
DROP TABLE "Afk";
|
||||
ALTER TABLE "new_Afk" RENAME TO "Afk";
|
||||
CREATE UNIQUE INDEX "Afk_userId_key" ON "Afk"("userId");
|
||||
PRAGMA foreign_keys=ON;
|
||||
PRAGMA defer_foreign_keys=OFF;
|
||||
10
prisma/migrations/20250628153216_birthday/migration.sql
Normal file
10
prisma/migrations/20250628153216_birthday/migration.sql
Normal file
@@ -0,0 +1,10 @@
|
||||
-- CreateTable
|
||||
CREATE TABLE "Birthday" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"userId" TEXT NOT NULL,
|
||||
"date" TEXT NOT NULL,
|
||||
"sent" BOOLEAN NOT NULL DEFAULT false
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "Birthday_userId_key" ON "Birthday"("userId");
|
||||
12
prisma/migrations/20250628162223_suggestions/migration.sql
Normal file
12
prisma/migrations/20250628162223_suggestions/migration.sql
Normal file
@@ -0,0 +1,12 @@
|
||||
-- CreateTable
|
||||
CREATE TABLE "Suggestion" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"userId" TEXT NOT NULL,
|
||||
"msgId" TEXT NOT NULL
|
||||
);
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "Suggestion_userId_key" ON "Suggestion"("userId");
|
||||
|
||||
-- CreateIndex
|
||||
CREATE UNIQUE INDEX "Suggestion_msgId_key" ON "Suggestion"("msgId");
|
||||
22
prisma/migrations/20250628162355_up_or_down/migration.sql
Normal file
22
prisma/migrations/20250628162355_up_or_down/migration.sql
Normal file
@@ -0,0 +1,22 @@
|
||||
/*
|
||||
Warnings:
|
||||
|
||||
- Added the required column `upDown` to the `Suggestion` table without a default value. This is not possible if the table is not empty.
|
||||
|
||||
*/
|
||||
-- RedefineTables
|
||||
PRAGMA defer_foreign_keys=ON;
|
||||
PRAGMA foreign_keys=OFF;
|
||||
CREATE TABLE "new_Suggestion" (
|
||||
"id" INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
|
||||
"userId" TEXT NOT NULL,
|
||||
"msgId" TEXT NOT NULL,
|
||||
"upDown" INTEGER NOT NULL
|
||||
);
|
||||
INSERT INTO "new_Suggestion" ("id", "msgId", "userId") SELECT "id", "msgId", "userId" FROM "Suggestion";
|
||||
DROP TABLE "Suggestion";
|
||||
ALTER TABLE "new_Suggestion" RENAME TO "Suggestion";
|
||||
CREATE UNIQUE INDEX "Suggestion_userId_key" ON "Suggestion"("userId");
|
||||
CREATE UNIQUE INDEX "Suggestion_msgId_key" ON "Suggestion"("msgId");
|
||||
PRAGMA foreign_keys=ON;
|
||||
PRAGMA defer_foreign_keys=OFF;
|
||||
@@ -0,0 +1,2 @@
|
||||
-- DropIndex
|
||||
DROP INDEX "Suggestion_userId_key";
|
||||
2
prisma/migrations/20250628163113_aaaa/migration.sql
Normal file
2
prisma/migrations/20250628163113_aaaa/migration.sql
Normal file
@@ -0,0 +1,2 @@
|
||||
-- DropIndex
|
||||
DROP INDEX "Suggestion_msgId_key";
|
||||
3
prisma/migrations/migration_lock.toml
Normal file
3
prisma/migrations/migration_lock.toml
Normal file
@@ -0,0 +1,3 @@
|
||||
# Please do not edit this file manually
|
||||
# It should be added in your version-control system (e.g., Git)
|
||||
provider = "sqlite"
|
||||
52
prisma/schema.prisma
Normal file
52
prisma/schema.prisma
Normal file
@@ -0,0 +1,52 @@
|
||||
// This is your Prisma schema file,
|
||||
// learn more about it in the docs: https://pris.ly/d/prisma-schema
|
||||
|
||||
// Looking for ways to speed up your queries, or scale easily with your serverless or edge functions?
|
||||
// Try Prisma Accelerate: https://pris.ly/cli/accelerate-init
|
||||
|
||||
generator client {
|
||||
provider = "prisma-client-js"
|
||||
binaryTargets = ["native", "debian-openssl-3.0.x"]
|
||||
}
|
||||
|
||||
datasource db {
|
||||
provider = "sqlite"
|
||||
url = "file:./vinci.db"
|
||||
}
|
||||
|
||||
model AiChat {
|
||||
id Int @id @default(autoincrement())
|
||||
messageid String @unique
|
||||
threadid String @unique
|
||||
messages AiMessage[]
|
||||
}
|
||||
|
||||
model AiMessage {
|
||||
id Int @id @default(autoincrement())
|
||||
role String
|
||||
content String
|
||||
|
||||
aiChatId Int
|
||||
aiChat AiChat @relation(fields: [aiChatId], references: [id])
|
||||
}
|
||||
|
||||
model Afk {
|
||||
id Int @id @default(autoincrement())
|
||||
userId String @unique
|
||||
reason String
|
||||
}
|
||||
|
||||
model Birthday {
|
||||
id Int @id @default(autoincrement())
|
||||
userId String @unique
|
||||
date String
|
||||
sent Boolean @default(false)
|
||||
}
|
||||
|
||||
model Suggestion {
|
||||
id Int @id @default(autoincrement())
|
||||
userId String
|
||||
msgId String
|
||||
upDown Int
|
||||
}
|
||||
|
||||
@@ -1,7 +0,0 @@
|
||||
import mongoose from 'mongoose'
|
||||
const schema = new mongoose.Schema({
|
||||
id: {type: String, required: true},
|
||||
reason: {type: String, required: true},
|
||||
});
|
||||
const db = mongoose.model('afk', schema, 'afk');
|
||||
export default db
|
||||
@@ -1,8 +0,0 @@
|
||||
import mongoose from 'mongoose'
|
||||
const schema = new mongoose.Schema({
|
||||
id: {type: String, required: true},
|
||||
date: {type: String, required: true},
|
||||
alreadysent: {type: Boolean, required: true},
|
||||
});
|
||||
const db = mongoose.model('birthday', schema, 'birthdays');
|
||||
export default db
|
||||
@@ -1,12 +0,0 @@
|
||||
import mongoose from 'mongoose'
|
||||
const messageSchema = new mongoose.Schema({
|
||||
role: { type: String, required: true },
|
||||
content: { type: String, required: true },
|
||||
});
|
||||
const schema = new mongoose.Schema({
|
||||
messageid: { type: String, required: true },
|
||||
threadid: { type: String, required: true },
|
||||
messages: { type: [messageSchema], required: true },
|
||||
});
|
||||
const db = mongoose.model('chatgpt', schema, 'chatgpt');
|
||||
export default db
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user