-
Notifications
You must be signed in to change notification settings - Fork 938
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
cc: add functions and triggers for components and modals #1619
cc: add functions and triggers for components and modals #1619
Conversation
@Ranger-4297 pointed out a really smart potential change re: adding components to messages. We've come up with a potential alternative to using
The solution we have come up with is this: {{ $msg := complexMessage "buttons" ( cslice ( sdict … ) ( sdict … ) ) "menus" ( cslice ( sdict … ) ( sdict … ) ) }} Pros
Cons
My proposal is thus: Keep the current functionality with buttons and menus in |
This is just a suggestion, but what I would do is place all new interaction context functions to separate file, |
I don't personally love the idea of putting the general functions in an "interactions" file because they're not really related to interactions, they are just object functions which dictate features of a message. You could use disabled buttons purely for aesthetics and never call a CC interaction. I feel that something such as |
For what it is worth, I don't think the naming is an issue and would prefer to see a separate file. |
functions: CreateComponent, CreateButton, CreateSelectMenu, CreateModal, distributeComponents, validateCustomID, validateActionRowsCustomIDs methods: tmplEditInteractionResponse, tmplEphemeralResponse, tmplGetResponse, tmplSendModal, tmplSendInteractionResponse, tmplUpdateMessage, tokenArg are all tied to interactions and sum up around 800 lines of code... seeing these separate makes more sense to me also in assets/customcommands-edit.html > "Custom ID Regex" does not really say much to regular user and it should be at least "Component (Custom) ID Regex" |
Is anything specific pending in this @SoggySaussages ? |
Apart from the needed changes given joe's recent js refactor, we were hoping to get the new documentation up and running first so we could thoroughly document the new features on release, given that they are a bit of a complex concept. |
all interaction related stuff should still be in a separate file like context_interactions.go, like I said on Mar 18th |
@SoggySaussages I agree with this it would make the code cleaner keeping all interaction related stuff in a different file. |
Oh sorry, I could've sworn I pushed that change, I did change that locally and will push when I get home. |
Co-Authored-By: Shadow <[email protected]> Co-Authored-By: Borbot33 <[email protected]> Co-Authored-By: Luca Zeuch <[email protected]>
creating buttons and select menus does not need context to run, and therefore should be in `general`. also renamed the functions to match convention
Move all custom id validation, including setting link button cids to empty strings, to one function executed at the end of a complexMessage or complexMessageEdit run. also moves the setting of default custom ids to this function. Signed-off-by: SoggySaussages <[email protected]>
add fields to complexMessage allowing users to pass slices of buttons and menus to complexMessage builders, in any order, as many times as they'd like. they can be slices of buttons/modals or sdicts. Signed-off-by: SoggySaussages <[email protected]>
allow multiple of the same key to be passed to complexMessage so that embeds and components may be declared multiple times, each case appending the input to the message. illustrated here: https://github.com/botlabs-gg/yagpdb/assets/110698921/c2e1e9fa-8f36-4ddd-8fd0-d45f4ad945d6 this is mainly implemented for buttons and menus since embed already uses a slice of embeds and this can be done even better using that method. this is not as simple with buttons and menus because we need to be able to customize the layout of the component rows. only keeping it the same for embed field for consistency. Signed-off-by: SoggySaussages <[email protected]>
Fix an issue re: "cc: restructure custom id validation" where components were no longer prepending templates- to custom ids Reverted an upstream pull in lib/discordgo.components.go, upstream discordgo uses strings whilst yagpdb uses int64
Implement the proper unmarshalling function from upstream discordgo to fix improper unmarshalling of message components
Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
adds aliases for the styles to be their numerical value or a discordgo.ButtonStyle, useful if using structToSdict so you don't need to manually parse the styles Signed-off-by: SoggySaussages <[email protected]>
add the ability for a file specified in complexMessage to be sent in an interaction response or followup. Technically a fix because I thought it would already work but never tested it. Feauring a slightly altered upstream pull of discordgo for (s *Session) CreateInteractionResponse. It still diverges from upstream slightly, however only enough to avoid rebasing the entirety of restapi.go. Signed-off-by: SoggySaussages <[email protected]>
use cutPrefix in modal handler. do not prepend templates- if it is already prefixxed, either from a structToSdict or a user thinking they have to. also validate cid length.
CustomID has custom ID with prefix templates- trimmed off. Cmd now has Cmd as matched by the regex pattern instead of the full custom ID. CmdArgs has the proper CmdArgs as would usually be parsed, Values has any values submitted in a menu or modal instead. Signed off by SoggySaussages <[email protected]>
getResponse allows the user to get an interaction response or followup. It functions similarly to getMessage, and takes an interaction token (nil to use token in context) and a message id (nil to get original response). This is necessary for getting ephemeral messages. Syntax: getResponse interactionToken mID Signed-off-by: SoggySaussages <[email protected]>
fixes a bug where editing a message to have no content would error. Also allows for messages without content or embeds if they have components. Signed-off-by: SoggySaussages <[email protected]>
Change from using GetOriginalInteractionResponse to WebhookMessage. This is similar to upstream which uses WebhookMessage with a message ID "@original" as opposed to a separate function. WebhookMessage message ID is a string which may be a message ID or "@original." Signed-off by SoggySaussages <[email protected]>
This reverts commit 376513d.
Add support for EndpointWebhookMessage to use a string value for the message ID. This is necessary because the endpoint supports use of either an int64 message ID or @original. Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
Clarify trigger type and add info that these triggers are in beta. Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
b77118d
to
8108fc5
Compare
Rebased and updated with separate file for new functions and js fixes in accordance with 1646 (hopefully everything fit together smoothly) |
Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
Signed-off-by: SoggySaussages <[email protected]>
Allowing components in DMs allows for link buttons and disabled buttons (for cosmetic purposes) to be included. This does not add support for triggering custom commands via DM interactions, DM component usage is still ignored by CC. Note: This commit puts the Show Server Info button before other components. Signed-off-by: SoggySaussages <[email protected]>
This PR updates YAGPDB custom commands to allow use of newer Discord features. Specifically, the use of Message Components and Modals. The ability to receive these interactions also opens up the possibility of interaction responses, which this PR also adds.
Changelog:
CustomCommandInteraction
type value.CustomCommandInteraction
type value which is a pointer to a discordgo.Interaction with a RespondedTo field. This variable is set and pointer added to context upon interaction creation, allowing for theRespondedTo
field to accurately reflect whether the bot has responded to an interaction yet across different cc executions from the same response. This dictates logic that decides whether the bot should send a "response" or a "followup" when asked to send a message re: an interaction.context.SendResponse
function to use a newsendMessageType
value instead ofisDM
. Since a response may now need to be sent as either a guild channel message, a dm, an interaction response, or an interaction followup, this new type covers our bases.context.SendResponse
can now send a response as an interaction response or a followup if the triggering CC is triggered by an interaction. The bot will decide whether to send an original response or a followup based on if the interaction has been responded to already or not. It will respond ephemerally ifephemeralResponse
function is used.editResponse,
andeditResponseNoEscape
.editResponse
works similarly toeditMessage
, but is used to edit interaction responses. While most interaction responses and followup messages can be edited witheditMessage
(given the bot has the right permissions in the channel), ephemeral responses must be edited using a different endpoint, thus necessitatingeditResponse
. It uses the following syntax:editResponse interactionToken msgID msg
.interactionToken
can be either a token ornil
to use the current interaction token in context (the one which triggered the cc).msgID
can either be a message ID, required for editing a followup message, ornil
, to edit the original interaction response.msg
functions the same aseditMessage
.ephemeralResponse
, which causes the response message to be sent ephemerally if the command was triggered by an interaction.sendModal
, which sends the provided modal as an interaction response. syntax issendModal modal
wheremodal
takes a modal value which can be created withcmodal
. SincesendModal
may only be run as an interaction response, it takes nointeractionToken
argument, and will only respond to the interaction triggering the cc.sendResponse
,sendResponseNoEscape
,sendResponseNoEscapeRetID
, andsendResponseRetID
. These function similarly to theirsendMessage
counterparts. They will either send an original interaction response or a followup based on whether the interaction has already been responded to. They use the syntaxsendMessage interactionToken msg
, whereinteractionToken
can either be a token ornil
, to use the current token in context (the interaction which triggered the command).msg
functions the same assendMessage
. You cannot send an original interaction response to an interaction not triggered by the current command. i.e:if interactionToken != currentFrame.Interaction.Token { send a followup }
updateMessage
andupdateMessageNoEscape
. These function similarly toeditMessage
. it edits whichever message the triggering component (such as a button) was used on.updateMessage
sends an original interaction response, which differentiates it fromeditResponse
which may only send a followup. This distinction is necessary since if an admin would like the only response to a button to be the editing of the message, usingeditResponse
will not send an interaction response, and the triggering user will get an error saying the interaction failed regardless of whether it truly has. it follows the syntaxupdateMessage msg
.msg
functions similarly toeditMessage
. SinceupdateMessage
may only be run as an interaction response, it takes nointeractionToken
argument, and will only respond to the interaction triggering the cc.cbutton
to create buttons which can then be added tocomplexMessage
s orcomplexMessageEdit
s. It works similarly tocembed
, directly encoding and unmarshalling values into a button structure WITH THESE THREE EXCEPTIONS:style
field parses the string names of the different styles such asprimary
,green
,secondary
,link
as an alternative to integer values of the button types.link
argument to the builder, it will automatically correct this to theurl
field discord requires for link buttons. essentially adding an alias for theurl
field since the difference betweenlink
andurl
may be confusing to users.templates-
to any custom id to limit them to use within templates only.This function additionally has validation, and checks for the following errors:
cmenu
to create select menus which can then be added tocomplexMessage
s orcomplexMessageEdit
s. It works similarly tocembed
, directly encoding and unmarshalling values into a button structure WITH THESE TWO EXCEPTIONS:type
field parses the string names of the different types of select menu such asuser
,role
, ortext
instead of an integer value representing the type.templates-
to any custom id to limit them to use within templates only.This function additionally has validation, and checks for the following errors:
minValues
ormaxValues
argument providedvalue
fields within the provided optionscmodal
to create modals which can then be sent withsendModal
. Parsed manually because the developer in charge of designing modals at discord wants to see the world burn. Available fields aretitle
,custom_id
, andfields
, which takes aslice
ofsdict
s. The sdicts are encoded and unmarshalled intodiscordgo.TextInput
objects. Assigned a default custom id if not overridden. Also prependstemplates-
to a custom id if it is provided.complexMessage
to addcomponents
andephemeral
fields.ephemeral
adds the ephemeral flag to the message if the value is not falsey.components
takes either a single message component, a slice of message components, or a slice of slices of message components. If given a single component, it appends a new action row with that single component. If given a slice of components, it automatically distributes the provided components into action rows, trimming off any components which don't fit. It also errors if duplicate custom ids for the components are used. Providing a slice of slices of components allows custom organization of the components into rows. excess is trimmed off. Also assigns default custom ids to components if one is not provided.complexMessageEdit
to take acomponents
value working exactly the same as incomplexMessage
.templates-
. On the website, switching to these triggers disables the message edit toggle..
context data for components and modal submission-triggered CCs:.Interaction.Token
to be saved to database, allowing for subsequent CCs to send followup responses.This is a PR which has been in the works for about 15 months, ever since I first got a functional yag host and began my journey in golang. Special thanks to the team of incredible testers that helped me make this code more user friendly, widely applicable, and bug-free* over the past few weeks:
Sam
Black Wolf
OneBigLotus
EyesEyes
TOW.
Ranger
sado
Shizuka
Borbot
Henri
lzodd
(and also to all the people on the christopaganism server who have been live-testing my prototypes for a few months)
Please see some use cases we’ve come up with:
Sado’s UNO (uses ephemeral responses, select menus, buttons)
Question of the day (uses buttons, modals, ephemeral responses)
Verification (uses buttons, ephemeral responses)
Signed-off-by: SoggySaussages [email protected]