diff --git a/.github/CONTRIBUTING.md b/.github/CONTRIBUTING.md index b72bd8ed..62b1f312 100644 --- a/.github/CONTRIBUTING.md +++ b/.github/CONTRIBUTING.md @@ -10,7 +10,6 @@ General support queries and possible bugs in YAGPDB are **not** in scope and wil [support server]: https://discord.gg/4udtcA5 - ## Submission Guide Thanks for contributing to the YAGPDB documentation! Please take a moment to review this document in order to make the @@ -45,7 +44,7 @@ this process below. In your local clone, install the required dependencies via NPM by running the following command: ```shellsession -$ npm install +npm install ``` This will ensure that you can fully build the documentation site locally, including the custom syntax highlighting we @@ -117,7 +116,7 @@ In order to preview your changes locally, you will need to run a local instance you have Node.js (and NPM) and Hugo installed, you can do so by running the following command: ```shellsession -$ npm run dev +npm run dev ``` This will run a local server on `http://localhost:1313` that will automatically update whenever you save a file, though @@ -125,7 +124,7 @@ without our custom syntax highlighting. If you prefer to view the site as it wou following commands instead: ```shellsession -$ npm run build && npm run preview +npm run build && npm run preview ``` This will build the site, execute the highlighting post-processor, and run a local server on `http://localhost:4173`. diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md index 6e645a31..d9ae791b 100644 --- a/.github/PULL_REQUEST_TEMPLATE.md +++ b/.github/PULL_REQUEST_TEMPLATE.md @@ -1,4 +1,5 @@ **Terms** + - [ ] I have read and understood this project's [Contributing Guidelines](CONTRIBUTING.md) diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml new file mode 100644 index 00000000..986d6543 --- /dev/null +++ b/.github/workflows/lint.yml @@ -0,0 +1,17 @@ +name: Lint + +on: + pull_request: + paths: + - 'content/**/*.md' + +jobs: + lint-markdown: + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4 + - name: Lint markdown files + uses: actionshub/markdownlint@main + with: + filesToIgnoreRegex: 'all-commands.md|scripts/.*|.github/.*' diff --git a/.mdlrc b/.mdlrc new file mode 100644 index 00000000..fe2362ea --- /dev/null +++ b/.mdlrc @@ -0,0 +1,3 @@ +git_recurse true +ignore_front_matter true +style 'config/markdownlint.rb' diff --git a/README.md b/README.md index 5bfaaa6d..cf811284 100644 --- a/README.md +++ b/README.md @@ -26,8 +26,9 @@ Pages are written in Markdown with additional shortcodes provided by the Doks th documentation](<(https://getdoks.org/docs/start-here/getting-started/)>) for a complete list of features. If you are editing pages related to custom commands, note that codeblocks support a custom `yag` language for accurate -syntax highlighting—do not use `go`. However, this feature is only enabled in production builds for performance, so `npm run dev` will _not_ highlight `yag` codeblocks. Use `npm run build` followed by `npm run preview` instead if you need to verify -that code is highlighted correctly. +syntax highlighting—do not use `go`. However, this feature is only enabled in production builds for performance, so +`npm run dev` will _not_ highlight `yag` codeblocks. Use `npm run build` followed by `npm run preview` instead if you +need to verify that code is highlighted correctly. > [!TIP] > If you use VSCode, this project provides custom workspace snippets to insert callouts, which you can activate in diff --git a/config/markdownlint.rb b/config/markdownlint.rb new file mode 100644 index 00000000..a5f6cf2c --- /dev/null +++ b/config/markdownlint.rb @@ -0,0 +1,49 @@ +# Enable all rules; we'll configure some of them below. +all + +# MD001: Header levels should only increment by one level at a time. +# Normally, this is a fair rule, but it does not quite work for our cases, +# especially in our humongous functions list. So disable it. +exclude_rule 'MD001' + +# MD002: First header should be a top level header. +# Some files do not have a top-level header, because it doesn't make sense for +# them, or just looks incredibly stupid on the rendered page. So disable this +# entire rule. +exclude_rule 'MD002' + +# MD004: Unordered list style. +# Use dashes for unordered lists. All lists. Even sublists. +rule 'MD004', :style => :dash + +# MD013: Line length. +# Allow lines to be up to 120 characters long, see the .editorconfig file. +# We also ignore code blocks, because they are often long and should not be +# wrapped at all. Same goes for tables. +rule 'MD013', :line_length => 120, :ignore_code_blocks => true, :tables => false + +# MD024: Multiple headers with the same content. +# Allow multiple headers with the same content so long they are under different +# parent headers. +rule 'MD024', :allow_different_nesting => true + +# MD026: Trailling punctuation in header. +# Allow question marks (FAQ-style). +rule 'MD026', :punctuation => '.,;:!' + +# MD029: Ordered list item prefix. +# Should increase in numerical order. +rule 'MD029', :style => :ordered + +# MD033: Inline HTML. +# Allow certain HTML elements, because we use them for nicer page layout. +rule 'MD033', :allowed_elements => 'center, div, sup, br, kbd' + +# MD037: Spaces inside emphasis markers. +# This rule is broken. See https://github.com/markdownlint/markdownlint/issues/84 +exclude_rule 'MD037' + +# MD041: First line in file should be a top-level header. +# See comment to MD002. It makes no sense to set this to H2 for similar reasons, +# we have TOML frontmatter with an automatic h1 in the rendered page. +exclude_rule 'MD041' diff --git a/content/discord.md b/content/discord.md index 42df8a8b..ca8ebec3 100644 --- a/content/discord.md +++ b/content/discord.md @@ -1,7 +1,11 @@ -+++ -type = "redirect" -target = "https://discord.gg/4udtcA5" -title = "Discord" -+++ +--- +type: redirect +target: 'https://discord.gg/4udtcA5' +title: 'Discord' +--- - + diff --git a/content/docs/core/command-settings.md b/content/docs/core/command-settings.md index 5d4f13b7..fe9766d0 100644 --- a/content/docs/core/command-settings.md +++ b/content/docs/core/command-settings.md @@ -39,7 +39,7 @@ Flags and switches are **_not_** affected by your prefix setting. For example, if your prefix is `?`, a command usage with flags and/or switches is as follows: -``` +```txt ?wouldyourather -raw ``` diff --git a/content/docs/custom-commands/commands.md b/content/docs/custom-commands/commands.md index eec0bd1f..41e762c4 100644 --- a/content/docs/custom-commands/commands.md +++ b/content/docs/custom-commands/commands.md @@ -283,13 +283,13 @@ You must specify a channel to run time-based commands in even if the command doe A cron expression represents a set of times, using 5 space-separated fields. -Field name | Mandatory? | Allowed values | Allowed special characters --------------- | ---------- | -------------- | -------------------------- -Minutes | Yes | 0-59 | * / , - -Hours | Yes | 0-23 | * / , - -Day of month | Yes | 1-31 | * / , - ? -Month | Yes | 1-12 or JAN-DEC | * / , - -Day of week (DOW)| Yes | 0-6 or SUN-SAT | * / , - ? +| Field name | Mandatory? | Allowed values | Allowed special characters | +| -------------- | ---------- | -------------- | -------------------------- | +| Minutes | Yes | 0-59 | * / , - | +| Hours | Yes | 0-23 | * / , - | +| Day of month | Yes | 1-31 | * / , - ? | +| Month | Yes | 1-12 or JAN-DEC | * / , - | +| Day of week (DOW)| Yes | 0-6 or SUN-SAT | * / , - ? | To read more about the supported format of cron expressions, visit [Robfig's Cron package documentation - Expression Format](https://pkg.go.dev/github.com/robfig/cron/v3#hdr-CRON_Expression_Format). @@ -302,7 +302,7 @@ on Corntab Guru, but are not supported with YAGPDB. {{< /callout >}} -**Special Characters** +###### Special Characters - Asterisk ( * ) diff --git a/content/docs/fun/soundboard.md b/content/docs/fun/soundboard.md index a650b9a8..9c8d59f5 100644 --- a/content/docs/fun/soundboard.md +++ b/content/docs/fun/soundboard.md @@ -32,7 +32,6 @@ Do **not** fill in the URL if you are going uploaded from local files, and vice {{< /callout >}} - You have two options to upload sounds: - Upload with local files diff --git a/content/docs/moderation/advanced-automoderator/triggers.md b/content/docs/moderation/advanced-automoderator/triggers.md index 6c893dca..729c2767 100644 --- a/content/docs/moderation/advanced-automoderator/triggers.md +++ b/content/docs/moderation/advanced-automoderator/triggers.md @@ -156,7 +156,6 @@ This trigger will fire when a message matches the specified regular expression.[ - **Also match visually similar characters**
Whether to also match visually similar characters, like `Ĥéĺĺó`. (Default: off) - #### Message not matching Regex The inverse of [Message matches Regex](#message-matches-regex). See there for configuration. @@ -305,12 +304,11 @@ This trigger will fire when a message triggers Discord's Automod. -[^1]: The regular expression used to match links is the following: -(?i)([a-z\d]+://)([\w_-]+(?:(?:\.[\w_-]+)+))([\w.,@?^=%&:/~+#-]*[\w@?^=%&/~+#-]) +[^1]: The regular expression used to match links is the following:
+``(?i)([a-z\d]+://)([\w_-]+(?:(?:\.[\w_-]+)+))([\w.,@?^=%&:/~+#-]*[\w@?^=%&/~+#-])`` [^2]: Under the hood, the bot will only check the last 1000 messages in the channel. If you have a high-traffic channel in combination with an extremely long time frame, the bot could (theoretically) miss some messages. [^3]: The RegEx engine used in YAGPDB is RE2. Some features are not supported, like lookaheads and lookbehinds. See [regex101](https://regex101.com/?flavor=golang) for some help with writing RE2-compatible regular expressions. - diff --git a/content/docs/moderation/moderation-tools.md b/content/docs/moderation/moderation-tools.md index 693c7c60..54cdf738 100644 --- a/content/docs/moderation/moderation-tools.md +++ b/content/docs/moderation/moderation-tools.md @@ -112,23 +112,30 @@ To remove the requirement and make the reason optional, you may toggle this on ( #### Moderation DMs -Moderation DMs are template scripts (**3**) which are executed within the offending user's DM. Text output to the response will -be directly sent to the offending user. +Moderation DMs are template scripts (**3**) which are executed within the offending user's DM. Text output to the +response will be directly sent to the offending user. {{< link-card href="/docs/reference/templates/syntax-and-data" description="Templates Reference" target="_blank" >}} Additional template dot context data is available for Moderation Actions: - `{{.Reason}}`: The reason specified in the timeout. -- `{{.Author}}`: The author of the punishment, is a [user object](/docs/reference/templates/syntax-and-data#user). -- `{{.Duration}}`: The duration of the mod action as a [time.Duration format](/docs/reference/templates/syntax-and-data#time). +- `{{.Author}}`: The author of the punishment, is a [user object]. +- `{{.Duration}}`: The duration of the mod action as a [time.Duration format]. - `{{.HumanDuration}}`: The duration in a human friendly format (`1 hour and 3 minutes` for example). - `{{.WarningID}}`: The ID of the warning (when using the warn command). +[user object]: /docs/reference/templates/syntax-and-data#user +[time.Duration format]: /docs/reference/templates/syntax-and-data#time + +{{< callout context="danger" title="Danger: Template Execution Errors" icon="outline/alert-octagon" >}} + Any errors which occur in the template execution will not be logged by default. The offending user will only receive a DM from your server saying **Failed executing template.** Setting a [Moderation DM Error channel](#mod-channels) allows for the more detailed errors to be captured. +{{< /callout >}} + Moderation actions which send DMs are: - Timeout @@ -273,8 +280,8 @@ You may optionally send warnings to the mod log, this is enabled in the warnings [ClearWarnings Command Syntax](/docs/core/all-commands#clearwarnings) - Clears the warnings of a user. -[TopWarnings Command Syntax](/docs/core/all-commands#topwarnings) - Shows ranked list of warnings on the server, allowing you to turn -misbehavior into a fun minigame for your server members. +[TopWarnings Command Syntax](/docs/core/all-commands#topwarnings) - Shows ranked list of warnings on the server, +allowing you to turn misbehavior into a fun minigame for your server members. {{< callout context="tip" title="Tip: Taking Action on Warn Count" icon="outline/rocket" >}} diff --git a/content/docs/notifications/streaming.md b/content/docs/notifications/streaming.md index f9dfaf97..fab96116 100644 --- a/content/docs/notifications/streaming.md +++ b/content/docs/notifications/streaming.md @@ -6,7 +6,6 @@ description = "Spam your server with notifications when someone starts streaming Let everyone know that someone is currently streaming. - ### Streaming Feed {{< callout context="note" title="Note: Announcements may not Post" icon="outline/info-circle" >}} diff --git a/content/docs/notifications/youtube.md b/content/docs/notifications/youtube.md index 4181496b..5a6b241f 100644 --- a/content/docs/notifications/youtube.md +++ b/content/docs/notifications/youtube.md @@ -24,18 +24,17 @@ may need to scroll down a bit); then select a channel to post it to. For a visua - If you are unable to obtain a direct channel URL, similar to
-*https://youtube.com/channel/UCuAXFkgsw1L7xaCfnd5JJOw*, we also support the following URLs: +**, we also support the following URLs: -- Video links (https://youtube.com/watch?v=dQw4w9WgXcQ) -- Shorts links (https://youtube.com/shorts/pBZ_2pX_8mg) -- Share links (https://youtu.be/dQw4w9WgXcQ) -- Live links (https://youtube.com/live/jfKfPfyJRdk) -- Playlist links (https://youtube.com/playlist?list=PLEamUZtdyTMxwDNQ97Y7im8EwqRyht12R) +- Video links () +- Shorts links () +- Share links () +- Live links () +- Playlist links () -Although we make an attempt at extracting the channel from usernames (https://youtube.com/user/MontyPython), -custom links (https://youtube.com/c/Taskmaster), and handles (https://youtube.com/@TomScottGo), these are not as +Although we make an attempt at extracting the channel from usernames (), +custom links (), and handles (), these are not as reliable as the links listed above, as we use the first result of a YouTube search to determine the channel via these URLs. diff --git a/content/docs/reference/custom-command-examples.md b/content/docs/reference/custom-command-examples.md index 66b6dbb3..9de1a006 100644 --- a/content/docs/reference/custom-command-examples.md +++ b/content/docs/reference/custom-command-examples.md @@ -221,7 +221,7 @@ You don't have any notes :( {{end}} ``` -### Cooldown Example +### Cooldown Example With YAGPDB's database system, you can now add cooldowns to you custom commands. You can either make them global cooldowns or a per user cooldown. diff --git a/content/docs/reference/custom-commands-limits.md b/content/docs/reference/custom-commands-limits.md index 9c0d7bce..bbeeb3fb 100644 --- a/content/docs/reference/custom-commands-limits.md +++ b/content/docs/reference/custom-commands-limits.md @@ -6,82 +6,86 @@ description = "Limits? I'm at my limit!" Various limits in YAGPDB custom commands (CC) for smooth functioning of the bot and misuse prevention. -## OVERALL +## Overall -* **Max amount of CCs:** 100/250 (free/prem) -* **Max CCs that can be triggered by a single action:** 3/5 (free/prem) -* **Character limit:** 10k (5k for join/leave msg, warn dm, etc...) -* **Limit writer:** 25kB -* **Max operations:** 1M/2.5M (free/prem) -* **Response Character Limit:** 2k -* **Generic API based Action call limit:** 100 per CC -* **State Lock based Actions:** 500 per CC (mentionRoleName/ID ; hasRoleName ; targetHasRoleName/ID) +- **Max amount of CCs:** 100/250 (free/prem) +- **Max CCs that can be triggered by a single action:** 3/5 (free/prem) +- **Character limit:** 10k (5k for join/leave msg, warn dm, etc...) +- **Limit writer:** 25kB +- **Max operations:** 1M/2.5M (free/prem) +- **Response Character Limit:** 2k +- **Generic API based Action call limit:** 100 per CC +- **State Lock based Actions:** 500 per CC (mentionRoleName/ID ; hasRoleName ; targetHasRoleName/ID) -## CALLING A CC +## Calling a Custom Command ### execCC -* **Calls per CC:** 1/10 (free/prem) -> counter key "runcc" -* **StackDepth limit:** 2 (executing with 0 delay) -* **Delay limit:** int64 limit (292 years) +- **Calls per CC:** 1/10 (free/prem) -> counter key "runcc" +- **StackDepth limit:** 2 (executing with 0 delay) +- **Delay limit:** int64 limit (292 years) ### scheduleUniqueCC -* **Calls per CC:** 1/10 (free/prem) -> counter key "runcc" -* **Delay limit:** int64 limit (292 years) -* There can only be 1 per server per key +- **Calls per CC:** 1/10 (free/prem) -> counter key "runcc" +- **Delay limit:** int64 limit (292 years) +- There can only be 1 per server per key ### cancelScheduledUniqueCC -* **Calls per CC:** 10/10 (free/prem) -> counter key "cancelcc" - -## CONTEXT - -* **Max file size (complexMessage):** 100kB -* **joinStr max string length:** 1000kB -* **sendDM:** 1 call per CC -> counter key "send\_dm" -* **sendTemplate/sendTemplateDM:** 3 calls per CC -> counter key "exec\_child" -* **addReactions:** 20 calls per CC -> counter key "add\_reaction\_trigger". Each reaction added counts towards the limit. -* **addResponseReactions:** 20 calls per CC -> counter key "add\_reaction\_response". Each reaction added counts towards the limit. -* **addMessageReactions:** 20 calls per CC -> counter key "add\_reaction\_message". Each reaction added counts towards the limit. -* **deleteMessageReaction: 1**0 calls per CC -> counter key "del\_reaction\_message". Each removed added counts towards the limit. -* **editChannelName/Topic:** 10 calls per CC -> counter key "edit\_channel" -* **regex cache limit:** 10 (this means you cant have more than 10 different regexes on a CC) -* **onlineCount:** 1 call per cc -> counter key "online\_users" -* **onlineCountBots:** 1 call per cc -> counter key "online\_bots" -* **editNickname:** 2 calls per cc -> counter key "edit\_nick" -* **Append/AppendSlice limit:** 10k size limit of resulting slice -* **exec/execAdmin:** 5 calls per cc -> no key -* **deleteResponse/deleteMessage/deleteTrigger max delay:** 86400s -* **take/removeRoleID/Name max delay:** int64 limit (292 years) -* **sleep:** 60 seconds +- **Calls per CC:** 10/10 (free/prem) -> counter key "cancelcc" + +## Context + +- **Max file size (complexMessage):** 100kB +- **joinStr max string length:** 1000kB +- **sendDM:** 1 call per CC -> counter key "send\_dm" +- **sendTemplate/sendTemplateDM:** 3 calls per CC -> counter key "exec\_child" +- **addReactions:** 20 calls per CC -> counter key "add\_reaction\_trigger". Each reaction added counts towards the + limit. +- **addResponseReactions:** 20 calls per CC -> counter key "add\_reaction\_response". Each reaction added counts towards + the limit. +- **addMessageReactions:** 20 calls per CC -> counter key "add\_reaction\_message". Each reaction added counts towards + the limit. +- **deleteMessageReaction: 1**0 calls per CC -> counter key "del\_reaction\_message". Each removed added counts towards + the limit. +- **editChannelName/Topic:** 10 calls per CC -> counter key "edit\_channel" +- **regex cache limit:** 10 (this means you cant have more than 10 different regexes on a CC) +- **onlineCount:** 1 call per cc -> counter key "online\_users" +- **onlineCountBots:** 1 call per cc -> counter key "online\_bots" +- **editNickname:** 2 calls per cc -> counter key "edit\_nick" +- **Append/AppendSlice limit:** 10k size limit of resulting slice +- **exec/execAdmin:** 5 calls per cc -> no key +- **deleteResponse/deleteMessage/deleteTrigger max delay:** 86400s +- **take/removeRoleID/Name max delay:** int64 limit (292 years) +- **sleep:** 60 seconds ## DATABASE ### Overall Limits -* **Max amount of DBs:** Membercount \*50\*1/10(free/prem) -* **Key length limit:** 256 -* **Expire limit:** int64 limit (292 years) -* **Value size limit:** 100kB +- **Max amount of DBs:** Membercount \*50\*1/10(free/prem) +- **Key length limit:** 256 +- **Expire limit:** int64 limit (292 years) +- **Value size limit:** 100kB ### Database Interactions -* **Calls per CC:** 10/50 (free/prem) -> counter key "db\_interactions" -* Valid for all database commands -> - * dbDel/dbDelByID - * dbGet - * dbIncr - * dbSet/dbSetExpire +- **Calls per CC:** 10/50 (free/prem) -> counter key "db\_interactions" +- Valid for all database commands -> + - dbDel/dbDelByID + - dbGet + - dbIncr + - dbSet/dbSetExpire ### Database Multiple Entry Interactions Multiple entries all count to general "db\_interactions" limit as well. -* **Calls per CC:** 2/10 (free/prem) -> counter key "db\_multiple" -* Valid for all database multiple entry related commands -> - * dbCount - * dbDelMultiple - * dbGetPattern - * dbRank - * dbTopEntries +- **Calls per CC:** 2/10 (free/prem) -> counter key "db\_multiple" +- Valid for all database multiple entry related commands -> + - dbCount + - dbDelMultiple + - dbGetPattern + - dbRank + - dbTopEntries diff --git a/content/docs/reference/custom-interactions.md b/content/docs/reference/custom-interactions.md index 37053c32..4fdf8d19 100644 --- a/content/docs/reference/custom-interactions.md +++ b/content/docs/reference/custom-interactions.md @@ -210,7 +210,7 @@ mentionable type select menus where an ID could be either a user or a role, `.Va you are parsing options from mentionable type menus, you will need to use your own methods of determining if an ID is a role or a user. -**Default Values** +###### Default Values Setting default values in these select menus is a more involved process than for text type menus. Instead of setting a `default` value on each option, you must instead provide a `default_values` argument containing a slice of @@ -242,7 +242,7 @@ it as an `int64`, which would not work. {{< /callout >}} -**Channel Type Filtering** +###### Channel Type Filtering A channel type menu optionally allows you to filter which channel types are made available for selection. You can use the `channel_types` argument which accepts a slice of [channel types](https://discord.com/developers/docs/resources/channel#channel-object-channel-types). @@ -602,9 +602,9 @@ with the trigger field `uno-`. This can take individual action for a button with ```yag {{ if eq .StrippedID "join" }} - {{ sendResponse nil "You joined the UNO game!" }} + {{ sendResponse nil "You joined the UNO game!" }} {{ else if eq .StrippedID "leave" }} - {{ sendResponse nil "You left the UNO game :(" }} + {{ sendResponse nil "You left the UNO game :(" }} {{ end }} ``` @@ -663,12 +663,12 @@ well. Possible initial responses: - Output text in your script response field. This text will be sent as an interaction response. - - You can even use the `ephemeralResponse` function to turn it _ephemeral_. + - You can even use the `ephemeralResponse` function to turn it _ephemeral_. - Use the `sendResponse` function to send a response as soon as the function runs. - - You can also use this to send `embeds` or `complexMessages`. - - You'll need to send a `complexMessage` and pass it `"ephemeral" true` as an argument to send _ephemeral_ messages. - - `sendResponse` comes in `NoEscape` and `RetID` variants too. - - When sending an initial response, `sendResponse` does not need an interaction token, `nil` can be used. + - You can also use this to send `embeds` or `complexMessages`. + - You'll need to send a `complexMessage` and pass it `"ephemeral" true` as an argument to send _ephemeral_ messages. + - `sendResponse` comes in `NoEscape` and `RetID` variants too. + - When sending an initial response, `sendResponse` does not need an interaction token, `nil` can be used. - Use the `sendModal` function to show the user a modal. You cannot respond to a user submitting a modal by sending them another modal. - Use the `updateMessage` function to edit the message the command triggered from. This works the same way as editing a @@ -686,24 +686,24 @@ interaction token of the interaction they should be following up on. Possible followups: - Output text in your script response field. This text will be sent as an interaction followup. - - You can even use the `ephemeralResponse` function to turn it _ephemeral_. + - You can even use the `ephemeralResponse` function to turn it _ephemeral_. - Use the `sendResponse` function to send a followup as soon as the function runs. Note that this function morphs into sending followups if an initial response has already been made. - - You can also use this to send `embeds` or `complexMessages`. - - `sendResponse` comes in `NoEscape` and `RetID` variants too. - - It's important to capture the message ID of any - followups you'll want to edit or retrieve later, especially if you followup ephemerally. If you followup ephemerally - without saving the message ID, you'll never be able to interface with that message again. + - You can also use this to send `embeds` or `complexMessages`. + - `sendResponse` comes in `NoEscape` and `RetID` variants too. + - It's important to capture the message ID of any + followups you'll want to edit or retrieve later, especially if you follow up ephemerally. If you follow up + ephemerally without saving the message ID, you'll never be able to interface with that message again. - Use the `editResponse` function to edit an initial response or a followup message. - - When editing an initial response, the `messageID` argument should be `nil`. - - When editing a followup message, the `messageID` argument is required. - - You can still edit any initial responses or followups using the standard `editMessage` function as long as they - aren't _ephemeral_. + - When editing an initial response, the `messageID` argument should be `nil`. + - When editing a followup message, the `messageID` argument is required. + - You can still edit any initial responses or followups using the standard `editMessage` function as long as they + aren't _ephemeral_. - Use the `getResponse` function to get an initial response or a followup message. - - When getting an initial response, the `messageID` argument should be `nil`. - - When getting a followup message, the `messageID` argument is required. - - You can still get any initial responses or followups using the standard `getMessage` function as long as they - aren't _ephemeral_. + - When getting an initial response, the `messageID` argument should be `nil`. + - When getting a followup message, the `messageID` argument is required. + - You can still get any initial responses or followups using the standard `getMessage` function as long as they + aren't _ephemeral_. [Interaction Function documentation](/docs/reference/templates/functions#interactions) diff --git a/content/docs/reference/how-to-get-ids.md b/content/docs/reference/how-to-get-ids.md index 285746a7..3662dc7f 100644 --- a/content/docs/reference/how-to-get-ids.md +++ b/content/docs/reference/how-to-get-ids.md @@ -6,16 +6,30 @@ description = "Snowflake? ID? I don't know, but this page does!" Details on obtaining IDs for users, channels, roles, etc. for use within YAGPDB. -**User IDs:** Can be found by mentioning the user then adding a \ such as `\@YAGPDB.xyz#8760` . Alternatively if you have developer mode on, you can right click and select Copy ID. [How to enable developer mode in Discord](https://support.discordapp.com/hc/en-us/articles/206346498-Where-can-I-find-my-User-Server-Message-ID-). +### User IDs -**Channel IDs:** Can be found by mentioning the channel then adding a \ such as `\#announcements`. Alternatively if you have developer mode on, you can right click on the channel and select Copy ID. +Can be found by mentioning the user then adding a \ such as `\@YAGPDB.xyz#8760`. Alternatively if you have +developer mode on, you can right-click and select Copy ID. [How to enable developer mode in Discord][devmode] -**Role IDs**: Use the `listroles`command. +[devmode]: https://support.discordapp.com/hc/en-us/articles/206346498-Where-can-I-find-my-User-Server-Message-ID- -**Emote IDs:** +### Channel IDs -If it is a **custom emote**, adding a \ in front of the emote such as `\:yag:` will display the name along with the ID such as `<:yag:277569741932068864>`. On an Android device remove backslash and enclose `:yag:` inside back-ticks `` `:yag:`. `` +Can be found by mentioning the channel then adding a \ such as `\#announcements`. Alternatively if you +have developer mode on, you can right-click on the channel and select Copy ID. -If it is an **animated emote**, do the same steps as a normal emote. If you do not have Discord Nitro, you can have a friend or a bot use the emote and right click on the emote to open its link. The ID will be a part of the URL. +### Role IDs -If it is a **default emote**, look up the Unicode for the emote on Google. Note that some of the more customized default emotes such as some of the family emotes will not work in any of the YAGPDB commands. +Use the `listroles` command. + +### Emoji IDs + +If it is a **custom emoji**, adding a \ in front of the emoji such as `\:yag:` will display the name along with the ID +such as `<:yag:277569741932068864>`. On an Android device remove backslash and enclose `:yag:` inside backticks +`` `:yag:`. `` + +If it is an **animated emoji**, do the same steps as a normal emoji. If you do not have Discord Nitro, you can have a +friend or a bot use the emoji and right-click on the emoji to open its link. The ID will be a part of the URL. + +If it is a **default emoji**, look up the Unicode for the emoji on Google. Note that some of the more customized default +emojis such as some of the family emojis will not work in any of the YAGPDB commands. diff --git a/content/docs/reference/regex.md b/content/docs/reference/regex.md index 5aed27df..dd883765 100644 --- a/content/docs/reference/regex.md +++ b/content/docs/reference/regex.md @@ -24,7 +24,8 @@ _As example, this will only match the word "Dinosaur":_ `(Dinosaur)` #### Don't match -Using `?:` after opening parenthesis of a capturing group creates a non-capturing group. Useful for example with template function `reFindAllSubmatches`. +Using `?:` after opening parenthesis of a capturing group creates a non-capturing group. Useful for example with +template function `reFindAllSubmatches`. _This will not sub-match the words "red, blue, green":_ \ ``{{ reFindAllSubmatches `(?:color=)(red|blue|green)` "color=red beautiful" }}`` @@ -34,7 +35,8 @@ To clarify more - it will not show `dateid,` because it's a whole match:\ #### Match A or B -You may also want to catch multiple options, for that we use a _"Vertical bar"_ or also known as a _"Pipe"_ between linux users. +You may also want to catch multiple options, for that we use a _"Vertical bar"_ or also known as a _"Pipe"_ between +Linux users. _As example, this will match if either "Cat" or "Dog" is present:_ `(Cat|Dog)` @@ -64,13 +66,14 @@ This will match every number: `([0-9])` #### Special Characters -Sometimes you have to use special characters but it may cause conflicts. In this case, you will have to use an escape character. +Sometimes you have to use special characters but it may cause conflicts. In this case, you will have to use an escape +character. For example, this is a star that doesn't interfere with other matches `\*`. ## Understanding Regex -If you still do not know what Regex are or want to know more. Check out the cheat sheet on the site below. +If you still do not know what Regex are or want to know more. Check out the cheat sheet on the site below. [computerhope.com](https://www.computerhope.com/jargon/r/regex.htm) diff --git a/content/docs/reference/templates/functions.md b/content/docs/reference/templates/functions.md index a8242986..7692c2e5 100644 --- a/content/docs/reference/templates/functions.md +++ b/content/docs/reference/templates/functions.md @@ -49,9 +49,8 @@ Creates a new forum post. Returns a channel object on success. - `name`: The post title. May not be empty. Must be a string. - `content`: the initial message's content; may be a string, an embed, or a complex message. May not be empty. - `values` (optional): Additional options for the post. May include: - - `"slowmode"`: The thread's slowmode in seconds. - - `"tags"`: One or more forum tag name or ID. Duplicate and invalid tags are ignored. - + - `"slowmode"`: The thread's slowmode in seconds. + - `"tags"`: One or more forum tag name or ID. Duplicate and invalid tags are ignored. #### createThread @@ -135,10 +134,10 @@ In addition to this, Discord limits the number of channel modifications to 2 per Edits the specified thread. - `opts`: a sdict containing the thread parameters to edit, supporting the following keys (all optional): - - `slowmode`: the thread's slowmode in seconds. - - `tags`: one or more forum tag name or ID. Duplicate and invalid tags are ignored. - - `auto_archive_duration`: how long the thread will show in the channel list after inactivity. - - `invitable`: whether non-moderators can add other members to the thread. Defaults to false. + - `slowmode`: the thread's slowmode in seconds. + - `tags`: one or more forum tag name or ID. Duplicate and invalid tags are ignored. + - `auto_archive_duration`: how long the thread will show in the channel list after inactivity. + - `invitable`: whether non-moderators can add other members to the thread. Defaults to false. #### getChannelOrThread @@ -241,11 +240,12 @@ Returns up to `amount` entries from the database, sorted in ascending order by t Returns the count of all matching database entries that are not expired. The argument must be one of the following: + - `userID`: count entries for the given user ID. - `pattern`: count only entries with keys matching the given pattern. - `query`: an sdict with the following (all optional) keys: - - `userID`: only count entries with a matching UserID field. Defaults to all UserIDs. - - `pattern`: only counts entries with keys matching the given pattern. Defaults to all keys. + - `userID`: only count entries with a matching UserID field. Defaults to all UserIDs. + - `pattern`: only counts entries with keys matching the given pattern. Defaults to all keys. #### dbDelByID @@ -264,9 +264,9 @@ Deletes a database entry under the given `userID` by its `ID`. Deletes up to `amount` entries from the database matching the given criteria. Returns the number of deleted entries. - `query`: an sdict with the following (all optional) keys: - - `userID`: only delete entries with a matching UserID field. Defaults to all UserIDs. - - `pattern`: only delete entries with keys matching the given pattern. Defaults to all keys. - - `reverse`: whether to delete entries with the lowest value first. Default is `false` (highest value first). + - `userID`: only delete entries with a matching UserID field. Defaults to all UserIDs. + - `pattern`: only delete entries with keys matching the given pattern. Defaults to all keys. + - `reverse`: whether to delete entries with the lowest value first. Default is `false` (highest value first). - `amount`: the maximum number of entries to delete, capped at 100. - `nSkip`: the number of entries to skip before deleting. @@ -335,9 +335,9 @@ Increments the value of the specified database entry by `incrBy`. Returns the ne Returns the rank of the specified entry in the set of entries as defined by `query`. - `query`: an sdict with the following (all optional) keys: - - `userID`: only include entries with the given user ID. - - `pattern`: only include entries with keys matching the given pattern. - - `reverse`: if `true`, entries with lower values have higher ranks. Default is `false`. + - `userID`: only include entries with the given user ID. + - `pattern`: only include entries with keys matching the given pattern. + - `reverse`: if `true`, entries with lower values have higher ranks. Default is `false`. #### dbSetExpire @@ -392,7 +392,6 @@ Numerical `dict` keys are retrieved as an `int64`, therefore you'd have to write Undoes the transformation performed by [`encodeBase64`](#encodebase64), converting the base64-encoded `string` back to its original form. - #### encodeBase64 ```yag @@ -537,16 +536,16 @@ about using interactions, [see here](/docs/reference/custom-interactions). Sends a modal to the member who triggered the interaction. - `modal`: an sdict with the following keys: - - `title`: the title of the modal. - - `custom_id`: a unique identifier for the modal. - - `fields`: a slice of sdicts with the following keys: - - `label`: the label for the field. - - `placeholder`: the placeholder text for the field. - - `value`: the default value for the field. - - `required`: whether the field is required. - - `style`: the style of the field (1 for short, 2 for long). - - `min_length`: the minimum length of the field. - - `max_length`: the maximum length of the field. + - `title`: the title of the modal. + - `custom_id`: a unique identifier for the modal. + - `fields`: a slice of sdicts with the following keys: + - `label`: the label for the field. + - `placeholder`: the placeholder text for the field. + - `value`: the default value for the field. + - `required`: whether the field is required. + - `style`: the style of the field (1 for short, 2 for long). + - `min_length`: the minimum length of the field. + - `max_length`: the maximum length of the field. Alternatively, you can create a modal object using the [`cmodal`](#cmodal) function. @@ -585,7 +584,6 @@ The following example must be triggered by a component or modal submission. {{ updateMessage $message }} ``` - #### updateMessageNoEscape ```yag @@ -1182,10 +1180,10 @@ Note that a message sent via [sendMessage](#sendmessage) is not the response---u Creates a complex message object for use in [editMessage](#editmessage) or [editMessageNoEscape](#editmessagenoescape). - `allowed_mentions`: an sdict with the following keys: - - `parse`: a slice of accepted values for mentions. May include `users`, `roles`, and `everyone`. - - `users`: a slice of user IDs to mention. - - `roles`: a slice of role IDs to mention. - - `replied_user`: whether to mention the replied user. + - `parse`: a slice of accepted values for mentions. May include `users`, `roles`, and `everyone`. + - `users`: a slice of user IDs to mention. + - `roles`: a slice of role IDs to mention. + - `replied_user`: whether to mention the replied user. - `content`: the new content for the message. - `embed`: an embed object or a slice of up to 10 embed objects. - `silent`: whether to suppress push and desktop notifications. @@ -1202,10 +1200,10 @@ for an example. Creates a complex message object for use in [sendMessage](#sendmessage) functions. - `allowed_mentions`: an sdict with the following keys: - - `parse`: a slice of accepted values for mentions. May include `users`, `roles`, and `everyone`. - - `users`: a slice of user IDs to mention. - - `roles`: a slice of role IDs to mention. - - `replied_user`: whether to mention the replied user. + - `parse`: a slice of accepted values for mentions. May include `users`, `roles`, and `everyone`. + - `users`: a slice of user IDs to mention. + - `roles`: a slice of role IDs to mention. + - `replied_user`: whether to mention the replied user. - `content`: the message content. - `embed`: an embed object or a slice of up to 10 embed objects. - `file`: the content to print as a file. @@ -1465,7 +1463,6 @@ Adds the first case-insensitive matching role name to the triggering member. - `delay`: an optional delay in seconds. - #### getRole ```yag @@ -1619,7 +1616,6 @@ the server. - `delay`: an optional delay in seconds. - #### takeRoleName ```yag @@ -1926,13 +1922,12 @@ local time zone of the host YAGPDB server. Returns the time object corresponding to -``` +```txt yyyy-mm-dd hh:mm:ss ``` In the appropriate zone for that time in the given location. - The month, day, hour, min, and sec values may be outside their usual ranges and will be normalized during the conversion. For example, October 32 converts to November 1. @@ -1989,7 +1984,6 @@ can be done using the `print` function: {{< /callout >}} - ---- ## Type conversion @@ -2055,7 +2049,6 @@ Converts the given string to a slice of runes (Unicode code points). Aliases: `str`. - ```yag {{ $str := toString }} ``` @@ -2125,20 +2118,20 @@ All keys are optional, but the Discord API will reject completey empty embeds, s - `description`: the main text - `color`: which color to display on the left side of the embed - `fields`: a slice of sdicts with the following keys: - - `name`: the name of the field - - `value`: which text to have inside this field - - `inline`: an optional boolean whether this field should be displayed in-line with other fields + - `name`: the name of the field + - `value`: which text to have inside this field + - `inline`: an optional boolean whether this field should be displayed in-line with other fields - `author`: Shows some details at the very top of the embed. Is an sdict with the following keys: - - `name`: The name of the author - - `url`: the URL to hyperlink the name with - - `icon_url`: the author's icon + - `name`: The name of the author + - `url`: the URL to hyperlink the name with + - `icon_url`: the author's icon - `thumbnail`: a small image in the top-right corner. Is an sdict with the following keys: - - `url`: the image's URL + - `url`: the image's URL - `image`: an image to display at full width at the bottom of the embed. Is an sdict with the following keys: - - `url`: the image's URL + - `url`: the image's URL - `footer`: Shows some details at the very bottom of the embed. Is an sdict with the following keys: - - `text`: the footer's text - - `icon_url`: a small icon to display to the left of the footer's text + - `text`: the footer's text + - `icon_url`: a small icon to display to the left of the footer's text - `timestamp`: a (static) timestamp to display to the right of the footer's text {{< callout context="tip" title="Tip: Custom Commands Embed Generator" icon="outline/rocket" >}} @@ -2262,7 +2255,7 @@ chaining `index` calls, e.g. `index (index $x 0) 1`. #### kindOf -``` +```yag {{ $kind := kindOf [indirect] }} ``` @@ -2302,8 +2295,8 @@ The result has the `.Get N` and `.IsSet N` methods available, returning the valu present, respectively, at position `N` (starting from 0). - `...cargs`: a list of argument definitions. Must have at least `requiredArgs` elements. Has the following arguments: - - `"type"`: the type of this argument as a quoted string. - - `"name"`: the name of this argument. Must be a string. + - `"type"`: the type of this argument as a quoted string. + - `"name"`: the name of this argument. Must be a string. An argument's `"type"` must be one of the following: @@ -2352,7 +2345,6 @@ of it. Creates a dictionary from the provided key-value pairs. The number of parameters must be even. The keys must be of string type. - #### sendTemplateDM ```yag @@ -2415,6 +2407,7 @@ start index and the subslice extends to the end of `item`. Returns the given list in a sorted order. The list's items must all be of the same type. The optional `options` argument is an sdict with the following (optional) keys: + - `key`: if sorting a list of maps, the key's value to sort by. This key must be present on all maps in the slice. - `reverse`: whether to sort in reverse (descending) order. Default: `false`. @@ -2427,4 +2420,3 @@ Limited to 1 call on regular servers and 3 calls on premium servers. ``` Returns a random verb. - diff --git a/content/docs/reference/templates/syntax-and-data.md b/content/docs/reference/templates/syntax-and-data.md index 17bec2ed..9b5556d9 100644 --- a/content/docs/reference/templates/syntax-and-data.md +++ b/content/docs/reference/templates/syntax-and-data.md @@ -425,6 +425,7 @@ Consider the following code: {{ end }} Hello! ``` + This program iterates ten *thousand* times, adding a newline and a tab character on every iteration to the output---we can fix this error by telling the bot to throw away (or "strip") whitespace characters by using the trim indicator `-`: @@ -748,9 +749,9 @@ function. Retrieving specific element inside _templates.Slice_ is by indexing it #### This section's snippets -- To demonstrate .StringSlice `{{(cslice currentTime.Month 42 "YAGPDB").StringSlice}}` will return a slice `[February -YAGPDB]`. If the flag would have been set to true - \{{...).StringSlice true\}}, all elements in that slice were not - strings and `` is returned. +- To demonstrate .StringSlice `{{(cslice currentTime.Month 42 "YAGPDB").StringSlice}}` will return a slice + `[February YAGPDB]`. If the flag would have been set to true - \{{...).StringSlice true\}}, all elements in that slice + were not strings and `` is returned. General example: @@ -809,8 +810,7 @@ types are now serialized properly, making manual conversion unnecessary. ## Database You have access to a basic set of Database functions having return of type _\*customcommands.LightDBEntry_ called here -[DBEntry](#dbentry). -This is almost a key value store ordered by the key and value combined. +[DBEntry](#dbentry). This is almost a key value store ordered by the key and value combined. You can have max 50 \* user_count (or 500 \* user_count for premium) values in the database, if you go above this all new write functions will fail, this value is also cached, so it won't be detected immediately when you go above nor diff --git a/content/docs/tools-and-utilities/autorole.md b/content/docs/tools-and-utilities/autorole.md index da67f637..c0eb47d8 100644 --- a/content/docs/tools-and-utilities/autorole.md +++ b/content/docs/tools-and-utilities/autorole.md @@ -4,7 +4,6 @@ weight = 710 description = "Automatically assign roles to members when they join." +++ - {{< callout context="note" title="Note: Required Permissions" icon="outline/info-circle" >}} Make sure that the bot has permission to manage roles **and** that the role the bot is assigning is below the highest @@ -21,14 +20,26 @@ works on members with no roles, rendering it useless if members are given roles ![Autorole view](overview_autorole.png) -The different parameters you can set up on this site are: +### Configuration -- **Automatically assign members this role**: Select the role that you want to bot to auto assign (only one role can be auto assigned). -- **Minutes of membership required for role**: Requires that a member must be on the server for `x` minutes before assigning the role. -- **Require one of these roles to be present on the member**: If a person does not have one of the following roles on them they will not be given a role. -- **Ignore people with the following roles**: If a person has one of the following roles on them they will not be given a role. -- **Only assign role when they join, do not give it back if it's removed from them afterwards**: Only assign the role to them once when they joined. If they lose the role sometime after, the bot will not give it back to them. Note that this means what it says - if this option is unticked and you remove this role manually from someone, it will be given back automatically. -- **Only assign the role after a member has completed Discord's Membership Screening**: The autorole will only assign the set role after member has completed the server's Membership Screening. +The different parameters you can set up on this site are: -**Retro-active full scan**\ -This feature is only available for premium users and it scans the server completely, assigning the autorole to the eligible members (if they don't have the role already). +- **Automatically assign members this role**: Select the role that you want to bot to auto assign (only one role can be + auto assigned). +- **Minutes of membership required for role**: Requires that a member must be on the server for `x` minutes before + assigning the role. +- **Require one of these roles to be present on the member**: If a person does not have one of the following roles on + them they will not be given a role. +- **Ignore people with the following roles**: If a person has one of the following roles on them they will not be given + a role. +- **Only assign role when they join, do not give it back if it's removed from them afterwards**: Only assign the role to + them once when they joined. If they lose the role sometime after, the bot will not give it back to them. Note that + this means what it says - if this option is unticked and you remove this role manually from someone, it will be given + back automatically. +- **Only assign the role after a member has completed Discord's Membership Screening**: The autorole will only assign + the set role after member has completed the server's Membership Screening. + +### Retroactive full scan + +This feature is only available for premium users and it scans the server completely, assigning the autorole to the +eligible members (if they don't have the role already). diff --git a/content/docs/tools-and-utilities/self-assignable-roles.md b/content/docs/tools-and-utilities/self-assignable-roles.md index 18ad75d1..f0ed2b08 100644 --- a/content/docs/tools-and-utilities/self-assignable-roles.md +++ b/content/docs/tools-and-utilities/self-assignable-roles.md @@ -86,7 +86,7 @@ Role groups have additional options that can be enabled/disabled by selecting th - Requiring a user to have one of the following role at all time (after initial assignment). - Removing the previous role when they assign themselves another role from the group. -#### Example usage: +#### Example usage Say you have a server with 3 factions and want people to be able to assign their own faction when they join. That's simple enough - all we have to do is: @@ -143,7 +143,8 @@ message with -skip flag. {{< /callout >}} -To set up a role menu, the related roles **have to be added to a role group**, then you invoke the command `-rolemenu create (role group name)` +To set up a role menu, the related roles **have to be added to a role group**, then you invoke the command +`-rolemenu create (role group name)`. The group mode and other restrictions from the role group and role still apply to the roles in the role menu. diff --git a/content/docs/welcome/premium.md b/content/docs/welcome/premium.md index 406d1db0..957d9fc7 100644 --- a/content/docs/welcome/premium.md +++ b/content/docs/welcome/premium.md @@ -136,9 +136,11 @@ Do not proceed unless you are hosting your own version of the YAGPDB codebase. When hosting YAGPDB yourself, you have access to a few methods to source premium slots to your users. - Patreon + 1. Configure your price per premium slot in `premium/patreonpremiumsource/patreonpremiumsource.go > func -CalcSlotsForPledge`. + CalcSlotsForPledge`. 2. Configure relevant env variables to connect YAGPDB to your Patreon API. + - Generating premium codes with the `GeneratePremiumCode` command. - Setting the `premium.all_guilds_premium` env variable to true. diff --git a/content/learn/beginner/conditional-branching.md b/content/learn/beginner/conditional-branching.md index a1ba2e74..c65ad7ee 100644 --- a/content/learn/beginner/conditional-branching.md +++ b/content/learn/beginner/conditional-branching.md @@ -70,7 +70,7 @@ write `if $s`, like so: {{< /callout >}} -#### Guard Clauses +### Guard Clauses As your code grows, you may find yourself nesting `if` statements inside each other. This can lead to code that is hard to read and understand. One way to avoid this is to use _guard clauses_. A guard clause is an `if` statement that checks @@ -201,7 +201,6 @@ a normal `if` conditional and only use `with` if it improves readability; do not {{< /callout >}} - ## Exercises 1. Write a Custom Command to determine if the number stored in a variable `$a` is even or odd and print `Number is Even` diff --git a/content/learn/beginner/variables-and-data-types.md b/content/learn/beginner/variables-and-data-types.md index b9da5d09..571d09bf 100644 --- a/content/learn/beginner/variables-and-data-types.md +++ b/content/learn/beginner/variables-and-data-types.md @@ -75,8 +75,9 @@ Please note that not all escape sequences are supported by Discord. It should become relatively clear that a lot of new lines and other special characters can make a quoted string quite hard to read. To make this easier, you can use backticks (`` ` ``) to create a _raw string literal_. A raw string -literal does not attempt to interpret its contents in any way, and will simply contain the text between the opening `` ` `` and closing `` ` `` unmodified---we cannot even escape a backtick to include one in the string, but we will later -cover functions that solve this special case. +literal does not attempt to interpret its contents in any way, and will simply contain the text between the opening +`` ` `` and closing `` ` `` unmodified---we cannot even escape a backtick to include one in the string, but we will +later cover functions that solve this special case. ```txt `This is my