diff options
| author | Austin Hellyer <[email protected]> | 2016-11-06 13:18:56 -0800 |
|---|---|---|
| committer | Austin Hellyer <[email protected]> | 2016-11-06 13:18:56 -0800 |
| commit | feb2ee1eddc92cf02fc9e64534030ae0d374418b (patch) | |
| tree | 301d5b1dea97cf797aeb3e94772b1973a68cac9a /src/ext/framework | |
| parent | Allow non-prefixed mentions (diff) | |
| download | serenity-feb2ee1eddc92cf02fc9e64534030ae0d374418b.tar.xz serenity-feb2ee1eddc92cf02fc9e64534030ae0d374418b.zip | |
Add an 'allow_whitespace' framework config
The option allows whitespace to be optional between a mention and a
command.
Setting it to true will allow the following scenario to occur, while
false will not:
```
<@BOT_ID>about
// bot process and executes the "about" command if it exists
```
Diffstat (limited to 'src/ext/framework')
| -rw-r--r-- | src/ext/framework/configuration.rs | 24 | ||||
| -rw-r--r-- | src/ext/framework/mod.rs | 91 |
2 files changed, 84 insertions, 31 deletions
diff --git a/src/ext/framework/configuration.rs b/src/ext/framework/configuration.rs index cd68c69..09874c8 100644 --- a/src/ext/framework/configuration.rs +++ b/src/ext/framework/configuration.rs @@ -4,6 +4,7 @@ use ::client::http; pub struct Configuration { pub depth: usize, pub on_mention: Option<Vec<String>>, + pub allow_whitespace: bool, pub prefix: Option<String>, } @@ -30,6 +31,28 @@ impl Configuration { self } + /// Whether to allow whitespace being optional between a mention and a + /// command. + /// + /// **Note**: Defaults to `false`. + /// + /// # Examples + /// + /// Setting this to `true` will allow this scenario to occur, while `false` + /// will not: + /// + /// ```ignore + /// <@BOT_ID>about + /// + /// // bot processes and executes the "about" command if it exists + /// ``` + pub fn allow_whitespace(mut self, allow_whitespace: bool) + -> Self { + self.allow_whitespace = allow_whitespace; + + self + } + pub fn prefix<S: Into<String>>(mut self, prefix: S) -> Self { self.prefix = Some(prefix.into()); @@ -42,6 +65,7 @@ impl Default for Configuration { Configuration { depth: 5, on_mention: None, + allow_whitespace: false, prefix: None, } } diff --git a/src/ext/framework/mod.rs b/src/ext/framework/mod.rs index 68acf0d..c504d53 100644 --- a/src/ext/framework/mod.rs +++ b/src/ext/framework/mod.rs @@ -32,63 +32,92 @@ impl Framework { #[doc(hidden)] pub fn dispatch(&mut self, context: Context, message: Message) { // Determine the point at which the prefix ends, and the command starts. - let pos = if let Some(ref prefix) = self.configuration.prefix { - if let Some(mention_ends) = self.find_mention_end(&message.content) { + let positions = if let Some(ref prefix) = self.configuration.prefix { + let pos = if let Some(mention_ends) = self.find_mention_end(&message.content) { mention_ends } else if !message.content.starts_with(prefix) { return; } else { prefix.len() + }; + + let mut positions = vec![pos]; + + if self.configuration.allow_whitespace { + positions.push(pos - 1); } + + positions } else if self.configuration.on_mention.is_some() { match self.find_mention_end(&message.content) { - Some(mention_end) => mention_end, + Some(mention_end) => { + let mut positions = vec![mention_end]; + + if self.configuration.allow_whitespace { + positions.push(mention_end - 1); + } + + positions + }, None => return, } } else { - 0 + vec![0] }; // Ensure that the message length is at least longer than the prefix // length. There's no point in checking further ahead if there's nothing // to check. - if message.content.len() <= pos { + let mut less_than = true; + + for position in &positions { + if message.content.len() > *position { + less_than = false; + + break; + } + } + + if less_than { return; } - let mut built = String::new(); + for position in positions { + let mut built = String::new(); - for i in 0..self.configuration.depth { - if i > 0 { - built.push(' '); - } + for i in 0..self.configuration.depth { + if i > 0 { + built.push(' '); + } - built.push_str(match { - message.content - .split_at(pos) - .1 - .split_whitespace() - .collect::<Vec<&str>>() - .get(i) - } { - Some(piece) => piece, - None => return, - }); + built.push_str(match { + message.content + .split_at(position) + .1 + .trim() + .split_whitespace() + .collect::<Vec<&str>>() + .get(i) + } { + Some(piece) => piece, + None => continue, + }); - if let Some(command) = self.commands.get(&built) { - if let Some(check) = self.checks.get(&built) { - if !(check)(&context, &message) { - return; + if let Some(command) = self.commands.get(&built) { + if let Some(check) = self.checks.get(&built) { + if !(check)(&context, &message) { + continue; + } } - } - let command = command.clone(); + let command = command.clone(); - thread::spawn(move || { - (command)(context, message) - }); + thread::spawn(move || { + (command)(context, message) + }); - return; + return; + } } } } |