Added helpFormat.

This commit is contained in:
Erik C. Thauvin 2020-03-31 22:34:35 -07:00
parent 559634fbfe
commit d2339044e6
32 changed files with 129 additions and 182 deletions

View file

@ -42,14 +42,6 @@ import java.util.Locale;
* @since 1.0
*/
public final class Constants {
/**
* The bot's private message command format.
*/
public static final String BOT_PRIVATE_CMD = "/msg %s ";
/**
* The bot's public message command format.
*/
public static final String BOT_PUB_CMD = "%s: ";
/**
* The connect/read timeout in ms.
*/

View file

@ -626,7 +626,7 @@ public class Mobibot extends PircBot {
send(sender, "Type a URL on " + ircChannel + " to post it.", isPrivate);
send(sender, "For more information on a specific command, type:", isPrivate);
send(sender,
Utils.helpIndent(Utils.botCommand(getNick(), isPrivate) + Constants.HELP_CMD + " <command>"),
Utils.helpIndent(Utils.helpFormat("%c " + Constants.HELP_CMD + " <command>", getNick(), isPrivate)),
isPrivate);
send(sender, "The commands are:", isPrivate);

View file

@ -51,6 +51,8 @@ import java.util.concurrent.TimeUnit;
* @since 1.0
*/
public final class Utils {
private static final String[] searchFlags = { "%c", "%n" };
/**
* Disables the default constructor.
*
@ -159,6 +161,20 @@ public final class Utils {
return colorize(s, Colors.DARK_GREEN);
}
/**
* Formats a help command by replacing {@code %c} with the bot's pub/priv command, and {@code %n} with the bot's
* nick.
*
* @param text The help command text.
* @param botNick The bot's nick.
* @param isPrivate The private flag.
* @return The formatted help command.
*/
public static String helpFormat(final String text, final String botNick, final boolean isPrivate) {
final String[] replace = { (isPrivate) ? "/msg " + botNick : botNick + ':', botNick };
return StringUtils.replaceEach(text, searchFlags, replace);
}
/**
* Returns indented help string.
*
@ -336,13 +352,4 @@ public final class Utils {
return date.format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm"));
}
public static String botCommand(final String name, boolean isPrivate) {
if (isPrivate) {
return String.format(Constants.BOT_PRIVATE_CMD, name);
} else {
return String.format(Constants.BOT_PUB_CMD, name);
}
}
}

View file

@ -54,7 +54,7 @@ abstract class AbstractCommand {
open fun helpResponse(bot: Mobibot, command: String, sender: String, isOp: Boolean, isPrivate: Boolean): Boolean {
if (!this.isOp || this.isOp == isOp) {
for (h in help) {
bot.send(sender, String.format(h, Utils.botCommand(bot.nick, isPrivate)), isPrivate)
bot.send(sender, Utils.helpFormat(h, bot.nick, isPrivate), isPrivate)
}
return true
}

View file

@ -40,7 +40,7 @@ class Cycle : AbstractCommand() {
override val command = "cycle"
override val help = listOf(
"To have the bot leave the channel and come back:",
Utils.helpIndent("%s $command")
Utils.helpIndent("%c $command")
)
override val isOp = true
override val isPublic = false

View file

@ -41,24 +41,24 @@ class Ignore(defaultIgnore: String) : AbstractCommand() {
init {
if (defaultIgnore.isNotBlank()) {
ignored.addAll(defaultIgnore.split(", +?| +"))
ignored.addAll(defaultIgnore.split(", *| +".toRegex()))
}
}
override val command = IGNORE_CMD
override val help = listOf(
"To ignore a link posted to the channel:",
Utils.helpIndent("https://www.foo.bar %s"),
Utils.helpIndent("https://www.foo.bar %n"),
"To check your ignore status:",
Utils.helpIndent("%s $command"),
Utils.helpIndent("%c $command"),
"To toggle your ignore status:",
Utils.helpIndent("%s $command $me")
Utils.helpIndent("%c $command $me")
)
private val helpOp = listOf(
"To ignore a link posted to the channel:",
Utils.helpIndent("https://www.foo.bar %s"),
Utils.helpIndent("https://www.foo.bar " + Utils.bold("%n"), false),
"To add/remove nicks from the ignored list:",
Utils.helpIndent("%s $command <nick>|$me [<nick> ...]")
Utils.helpIndent("%c $command <nick> [<nick> ...]")
)
override val isOp = false
@ -67,7 +67,7 @@ class Ignore(defaultIgnore: String) : AbstractCommand() {
companion object {
const val IGNORE_CMD = "ignore"
private val ignored = HashSet<String>()
private val ignored = TreeSet<String>()
@JvmStatic
fun isNotIgnored(nick: String): Boolean {
@ -101,7 +101,7 @@ class Ignore(defaultIgnore: String) : AbstractCommand() {
): Boolean {
return if (isOp) {
for (h in helpOp) {
bot.send(sender, String.format(h, bot.nick), isPrivate)
bot.send(sender, Utils.helpFormat(h, bot.nick, isPrivate), isPrivate)
}
true
} else {

View file

@ -41,7 +41,7 @@ class Info : AbstractCommand() {
override val command = "info"
override val help = listOf(
"To view information about the bot:",
Utils.helpIndent("%s $command")
Utils.helpIndent("%c $command")
)
override val isOp = false
override val isPublic = true

View file

@ -39,7 +39,7 @@ class Me : AbstractCommand() {
override val command = "me"
override val help = listOf(
"To have the bot perform an action:",
Utils.helpIndent("%s $command <action>")
Utils.helpIndent("%c $command <action>")
)
override val isOp = true
override val isPublic = false

View file

@ -39,7 +39,7 @@ class Modules : AbstractCommand() {
override val command = "modules"
override val help = listOf(
"To view a list of enabled modules:",
Utils.helpIndent("%s $command")
Utils.helpIndent("%c $command")
)
override val isOp = true
override val isPublic = false

View file

@ -39,7 +39,7 @@ class Msg : AbstractCommand() {
override val command = "msg"
override val help = listOf(
"To have the bot send a private message to someone:",
Utils.helpIndent("%s $command <nick> <text>")
Utils.helpIndent("%c $command <nick> <text>")
)
override val isOp = true
override val isPublic = true

View file

@ -39,7 +39,7 @@ class Nick : AbstractCommand() {
override val command = "nick"
override val help = listOf(
"To change the bot's nickname:",
Utils.helpIndent("%s $command <nick>")
Utils.helpIndent("%c $command <nick>")
)
override val isOp = true
override val isPublic = true

View file

@ -42,7 +42,7 @@ class Recap : AbstractCommand() {
override val command = "recap"
override val help = listOf(
"To list the last 10 public channel messages:",
Utils.helpIndent("%s $command")
Utils.helpIndent("%c $command")
)
override val isOp = false
override val isPublic = true
@ -67,7 +67,7 @@ class Recap : AbstractCommand() {
fun storeRecap(sender: String, message: String, isAction: Boolean) {
recaps.add(
Utils.utcDateTime(LocalDateTime.now(Clock.systemUTC()))
+ " -> ${sender}: " + (if (isAction) " " else ": ") + message
+ " - $sender" + (if (isAction) " " else ": ") + message
)
if (recaps.size > 10) {
recaps.removeAt(0)

View file

@ -39,7 +39,7 @@ class Say : AbstractCommand() {
override val command = "say"
override val help = listOf(
"To have the bot say something on the channel:",
Utils.helpIndent("%s $command <text>")
Utils.helpIndent("%c $command <text>")
)
override val isOp = true
override val isPublic = false

View file

@ -41,7 +41,7 @@ class Users : AbstractCommand() {
override val command = "users"
override val help = listOf(
"To list the users present on the channel:",
Utils.helpIndent("%s $command")
Utils.helpIndent("%c $command")
)
override val isOp = false
override val isPublic = true

View file

@ -98,7 +98,11 @@ class Comment : AbstractCommand() {
if (super.helpResponse(bot, command, sender, isOp, isPrivate)) {
if (isOp) {
bot.send(sender, "To change a comment's author:", isPrivate)
bot.send(sender, Utils.helpIndent("/msg ${bot.nick} ${Constants.LINK_CMD}1.1:?<nick>"), isPrivate)
bot.send(
sender,
Utils.helpIndent("${Constants.LINK_CMD}1.1:?<nick>"),
isPrivate
)
}
return true
}

View file

@ -51,7 +51,7 @@ class Posting : AbstractCommand() {
Utils.helpIndent("${Constants.LINK_CMD}1:This is a comment"),
"I will reply with a label, for example: ${Utils.bold(Constants.LINK_CMD)}1.1",
"To edit a comment, see: ",
Utils.helpIndent("%s ${Constants.HELP_CMD} ${Comment.COMMAND}")
Utils.helpIndent("%c ${Constants.HELP_CMD} ${Comment.COMMAND}")
)
override val isOp = false
override val isPublic = true

View file

@ -45,7 +45,7 @@ class View : AbstractCommand() {
override val command = VIEW_CMD
override val help = listOf(
"To list or search the current URL posts:",
Utils.helpIndent("%s $command [<start>] [<query>]")
Utils.helpIndent("%c $command [<start>] [<query>]")
)
override val isOp = false
override val isPublic = true

View file

@ -377,9 +377,10 @@ public class Tell extends AbstractCommand {
} else {
bot.send(sender, "To delete one or all delivered messages:", isPrivate);
bot.send(sender,
Utils.helpIndent(
Utils.botCommand(bot.getNick(), isPrivate) + TELL_CMD + ' ' + TELL_DEL_KEYWORD + " <id|"
+ TELL_ALL_KEYWORD + '>'),
Utils.helpIndent(Utils.helpFormat(
"%c " + TELL_CMD + ' ' + TELL_DEL_KEYWORD + " <id|" + TELL_ALL_KEYWORD + '>',
bot.getNick(),
isPrivate)),
isPrivate);
bot.send(sender,
"Messages are kept for " + Utils.bold(maxDays) + Utils.plural(maxDays, " day.", " days."),

View file

@ -33,6 +33,7 @@
package net.thauvin.erik.mobibot.modules;
import net.thauvin.erik.mobibot.Mobibot;
import net.thauvin.erik.mobibot.Utils;
import org.apache.commons.lang3.StringUtils;
import java.util.ArrayList;
@ -50,6 +51,7 @@ import java.util.concurrent.ConcurrentHashMap;
*/
public abstract class AbstractModule {
final List<String> commands = new ArrayList<>();
final List<String> help = new ArrayList<>();
final Map<String, String> properties = new ConcurrentHashMap<>();
/**
@ -95,14 +97,17 @@ public abstract class AbstractModule {
}
/**
* Responds with the module's Constants.
* @param bot The bot's instance.
* Responds with the module's help.
*
* @param bot The bot's instance.
* @param sender The sender.
* @param isPrivate Set to <code>true</code> if the response should be sent as a private message.
*/
public abstract void helpResponse(final Mobibot bot,
final String sender,
final boolean isPrivate);
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
for (final String h : help) {
bot.send(sender, Utils.helpFormat(h, bot.getNick(), isPrivateMsgEnabled() && isPrivate), isPrivate);
}
}
/**
* Returns <code>true</code> if the module is enabled.

View file

@ -56,7 +56,11 @@ public class Calc extends AbstractModule {
*/
public Calc() {
super();
commands.add(CALC_CMD);
help.add("To solve a mathematical calculation:");
help.add(Utils.helpIndent("%c " + CALC_CMD + " <calculation>"));
}
/**
@ -93,13 +97,4 @@ public class Calc extends AbstractModule {
helpResponse(bot, sender, isPrivate);
}
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
bot.send(sender, "To solve a mathematical calculation:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + CALC_CMD + " <calculation>"), isPrivate);
}
}

View file

@ -84,6 +84,7 @@ public final class CurrencyConverter extends ThreadedModule {
*/
public CurrencyConverter() {
super();
commands.add(CURRENCY_CMD);
}
@ -239,11 +240,15 @@ public final class CurrencyConverter extends ThreadedModule {
bot.send(sender, EMPTY_RATE_TABLE, isPrivate);
} else {
bot.send(sender, "To convert from one currency to another:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + CURRENCY_CMD + " 100 USD to EUR"), isPrivate);
bot.send(sender,
Utils.helpIndent(Utils.helpFormat("%c " + CURRENCY_CMD + " 100 USD to EUR",
bot.getNick(),
isPrivate)), isPrivate);
bot.send(sender, "For a listing of current rates:", isPrivate);
bot.send(sender,
Utils.helpIndent(bot.getNick() + ": " + CURRENCY_CMD) + ' ' + CURRENCY_RATES_KEYWORD,
isPrivate);
Utils.helpIndent(Utils.helpFormat("%c " + CURRENCY_CMD + ' ' + CURRENCY_RATES_KEYWORD,
bot.getNick(),
isPrivate)), isPrivate);
bot.send(sender, "The supported currencies are: ", isPrivate);
bot.sendCommandsList(sender, new ArrayList<>(EXCHANGE_RATES.keySet()), 11, isPrivate, false);
}

View file

@ -55,7 +55,11 @@ public final class Dice extends AbstractModule {
*/
public Dice() {
super();
commands.add(DICE_CMD);
help.add("To roll the dice:");
help.add(Utils.helpIndent("%c " + DICE_CMD));
}
/**
@ -92,13 +96,4 @@ public final class Dice extends AbstractModule {
bot.action("tied.");
}
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
bot.send(sender, "To roll the dice:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + DICE_CMD), isPrivate);
}
}

View file

@ -72,7 +72,12 @@ public final class GoogleSearch extends ThreadedModule {
*/
public GoogleSearch() {
super();
commands.add(GOOGLE_CMD);
help.add("To search Google:");
help.add(Utils.helpIndent("%c " + GOOGLE_CMD + " <query>"));
properties.put(GOOGLE_API_KEY_PROP, "");
properties.put(GOOGLE_CSE_KEY_PROP, "");
}
@ -137,19 +142,6 @@ public final class GoogleSearch extends ThreadedModule {
}
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
if (isEnabled()) {
bot.send(sender, "To search Google:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + GOOGLE_CMD + " <query>"), isPrivate);
} else {
bot.send(sender, "The Google search module is disabled.", isPrivate);
}
}
/**
* Searches Google.
*/

View file

@ -63,7 +63,11 @@ public final class Joke extends ThreadedModule {
*/
public Joke() {
super();
commands.add(JOKE_CMD);
help.add("To retrieve a random joke:");
help.add(Utils.helpIndent("%c " + JOKE_CMD));
}
/**
@ -120,13 +124,4 @@ public final class Joke extends ThreadedModule {
bot.send(sender, e.getMessage(), isPrivate);
}
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
bot.send(sender, "To retrieve a random joke:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + JOKE_CMD), isPrivate);
}
}

View file

@ -62,7 +62,11 @@ public final class Lookup extends AbstractModule {
*/
public Lookup() {
super();
commands.add(LOOKUP_CMD);
help.add("To perform a DNS lookup query:");
help.add(Utils.helpIndent("%c " + LOOKUP_CMD + " <ip address or hostname>"));
}
/**
@ -190,13 +194,4 @@ public final class Lookup extends AbstractModule {
helpResponse(bot, sender, true);
}
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
bot.send(sender, "To perform a DNS lookup query:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + LOOKUP_CMD + " <ip address or hostname>"), isPrivate);
}
}

View file

@ -74,7 +74,11 @@ public class Ping extends AbstractModule {
*/
public Ping() {
super();
commands.add(PING_CMD);
help.add("To ping the bot:");
help.add(Utils.helpIndent("%c " + PING_CMD));
}
/**
@ -89,13 +93,4 @@ public class Ping extends AbstractModule {
final SecureRandom r = new SecureRandom();
bot.action(PINGS.get(r.nextInt(PINGS.size())));
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
bot.send(sender, "To ping the bot:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + PING_CMD), isPrivate);
}
}

View file

@ -33,9 +33,9 @@
package net.thauvin.erik.mobibot.modules
import net.thauvin.erik.mobibot.Mobibot
import net.thauvin.erik.mobibot.Utils
import net.thauvin.erik.mobibot.Utils.bold
import net.thauvin.erik.mobibot.Utils.green
import net.thauvin.erik.mobibot.Utils.helpIndent
import net.thauvin.erik.mobibot.Utils.red
import kotlin.random.Random
@ -50,6 +50,16 @@ class RockPaperScissors : AbstractModule() {
add(Hands.PAPER.name.toLowerCase())
add(Hands.SCISSORS.name.toLowerCase())
}
with(help) {
add("To play Rock Paper Scissors:")
add(
Utils.helpIndent(
"%c ${Hands.ROCK.name.toLowerCase()} | ${Hands.PAPER.name.toLowerCase()}"
+ " | ${Hands.SCISSORS.name.toLowerCase()}"
)
)
}
}
enum class Hands(val action: String) {
@ -105,16 +115,4 @@ class RockPaperScissors : AbstractModule() {
}
}
}
override fun helpResponse(bot: Mobibot, sender: String, isPrivate: Boolean) {
bot.send(sender, "To play Rock Paper Scissors:", isPrivate)
bot.send(
sender,
helpIndent(
"${bot.nick}: ${Hands.ROCK.name.toLowerCase()} | ${Hands.PAPER.name.toLowerCase()}"
+ " | ${Hands.SCISSORS.name.toLowerCase()}"
),
isPrivate
)
}
}

View file

@ -79,6 +79,10 @@ public final class StockQuote extends ThreadedModule {
public StockQuote() {
super();
commands.add(STOCK_CMD);
help.add("To retrieve a stock quote:");
help.add(Utils.helpIndent("%c " + STOCK_CMD + " <symbol|keywords>"));
properties.put(ALPHAVANTAGE_API_KEY_PROP, "");
}
@ -200,15 +204,6 @@ public final class StockQuote extends ThreadedModule {
}
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
bot.send(sender, "To retrieve a stock quote:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + STOCK_CMD + " <symbol|keywords>"), isPrivate);
}
/**
* Returns the specified stock quote from Alpha Avantage.
*/

View file

@ -62,7 +62,12 @@ public final class Twitter extends ThreadedModule {
*/
public Twitter() {
super();
commands.add(TWITTER_CMD);
help.add("To post to Twitter:");
help.add(Utils.helpIndent("%c " + TWITTER_CMD + " <message>"));
properties.put(CONSUMER_SECRET_PROP, "");
properties.put(CONSUMER_KEY_PROP, "");
properties.put(TOKEN_PROP, "");
@ -110,19 +115,6 @@ public final class Twitter extends ThreadedModule {
}
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
if (isEnabled()) {
bot.send(sender, "To post to Twitter:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + TWITTER_CMD + " <message>"), isPrivate);
} else {
bot.send(sender, "The Twitter posting facility is " + Utils.bold("disabled") + '.', isPrivate);
}
}
/**
* Posts on Twitter.
*

View file

@ -60,7 +60,11 @@ public final class War extends AbstractModule {
*/
public War() {
super();
commands.add(WAR_CMD);
help.add("To play war:");
help.add(Utils.helpIndent("%c " + WAR_CMD));
}
/**
@ -97,13 +101,4 @@ public final class War extends AbstractModule {
bot.action("wins.");
}
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
bot.send(sender, "To play war:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + WAR_CMD), isPrivate);
}
}

View file

@ -75,7 +75,15 @@ public class Weather2 extends ThreadedModule {
*/
public Weather2() {
super();
commands.add(WEATHER_CMD);
help.add("To display weather information:");
help.add(Utils.helpIndent("%c " + WEATHER_CMD + " <city> [, <country code>]"));
help.add("For example:");
help.add(Utils.helpIndent("%c " + WEATHER_CMD + " paris, fr"));
help.add("The default ISO 3166 country code is " + bold("US") + ". Zip codes supported in most countries.");
properties.put(OWM_API_KEY_PROP, "");
}
@ -206,22 +214,6 @@ public class Weather2 extends ThreadedModule {
return Math.round(w) + " mph, " + Math.round(kmh) + " km/h";
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
bot.send(sender, "To display weather information:", isPrivate);
bot.send(sender,
Utils.helpIndent(bot.getNick() + ": " + WEATHER_CMD + " <city> [, <country code>]"),
isPrivate);
bot.send(sender, "For example:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + WEATHER_CMD + " paris, fr"), isPrivate);
bot.send(sender,
"The default ISO 3166 country code is " + bold("US")
+ ". Zip codes are supported in most countries.", isPrivate);
}
/**
* Fetches the weather data from a specific city.
*/

View file

@ -63,7 +63,6 @@ public final class WorldTime extends AbstractModule {
// Supported countries
private static final Map<String, String> COUNTRIES_MAP;
/**
* The time command.
*/
@ -160,9 +159,16 @@ public final class WorldTime extends AbstractModule {
*/
public WorldTime() {
super();
help.add("To display a country's current date/time:");
help.add(Utils.helpIndent("%c " + TIME_CMD) + " [<country code>]");
help.add("For a listing of the supported countries:");
help.add(Utils.helpIndent("%c " + TIME_CMD));
commands.add(TIME_CMD);
}
/**
* Returns the current Internet (beat) Time.
*
@ -234,18 +240,6 @@ public final class WorldTime extends AbstractModule {
}
}
/**
* {@inheritDoc}
*/
@Override
public void helpResponse(final Mobibot bot, final String sender, final boolean isPrivate) {
bot.send(sender, "To display a country's current date/time:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + TIME_CMD) + " [<country code>]", isPrivate);
bot.send(sender, "For a listing of the supported countries:", isPrivate);
bot.send(sender, Utils.helpIndent(bot.getNick() + ": " + TIME_CMD), isPrivate);
}
/**
* {@inheritDoc}
*/