issue #3 adding "commandline" feature
This commit is contained in:
parent
44b8d3328a
commit
3df015d132
10
cogs/help.py
10
cogs/help.py
@ -49,7 +49,7 @@ class Help:
|
||||
if page == '🏠':
|
||||
## POLL CREATION SHORT
|
||||
embed.add_field(name='🆕 Making New Polls',
|
||||
value=f'`{pre}quick` | `{pre}new` | `{pre}prepare`', inline=False)
|
||||
value=f'`{pre}quick` | `{pre}new` | `{pre}prepare` | `{pre}cmd <args>`', inline=False)
|
||||
# embed.add_field(name='Commands', value=f'`{pre}quick` | `{pre}new` | `{pre}prepared`', inline=False)
|
||||
# embed.add_field(name='Arguments', value=f'Arguments: `<poll question>` (optional)', inline=False)
|
||||
# embed.add_field(name='Examples', value=f'Examples: `{pre}new` | `{pre}quick What is the greenest color?`',
|
||||
@ -108,6 +108,14 @@ class Help:
|
||||
f'and/or if you would like to manually `{pre}activate` it. '
|
||||
'Perfect if you are preparing for a team meeting!',
|
||||
inline=False)
|
||||
embed.add_field(name=f'🔹 **-Advanced- Commandline:** `{pre}cmd <args>`',
|
||||
value=f'For the full syntax type `{pre}cmd help`\n'
|
||||
f'Similar to version 1 of the bot, with this command you can create a poll in one message. '
|
||||
f'Pass all the options you need via command line arguments, the rest will be set to '
|
||||
f'default values. The wizard will step in for invalid arguments.\n'
|
||||
f'Example: `{pre}cmd -q "Which colors?" -l colors -o "green, blue, red" -mc -a`',
|
||||
inline=False)
|
||||
|
||||
elif page == '🔍':
|
||||
embed.add_field(name='🔍 Show Polls',
|
||||
value='All users can display and list polls, with the exception of prepared polls. '
|
||||
|
||||
101
cogs/poll.py
101
cogs/poll.py
@ -165,7 +165,11 @@ class Poll:
|
||||
|
||||
while True:
|
||||
try:
|
||||
reply = await self.get_user_reply()
|
||||
if force:
|
||||
reply = force
|
||||
force = None
|
||||
else:
|
||||
reply = await self.get_user_reply()
|
||||
self.name = await get_valid(reply)
|
||||
await self.add_vaild(message, self.name)
|
||||
break
|
||||
@ -203,7 +207,11 @@ class Poll:
|
||||
|
||||
while True:
|
||||
try:
|
||||
reply = await self.get_user_reply()
|
||||
if force:
|
||||
reply = force
|
||||
force = None
|
||||
else:
|
||||
reply = await self.get_user_reply()
|
||||
self.short = await get_valid(reply)
|
||||
await self.add_vaild(message, self.short)
|
||||
break
|
||||
@ -263,7 +271,11 @@ class Poll:
|
||||
|
||||
while True:
|
||||
try:
|
||||
reply = await self.get_user_reply()
|
||||
if force:
|
||||
reply = force
|
||||
force = None
|
||||
else:
|
||||
reply = await self.get_user_reply()
|
||||
dt = await get_valid(reply)
|
||||
self.activation = dt
|
||||
if self.activation == 0:
|
||||
@ -315,7 +327,11 @@ class Poll:
|
||||
|
||||
while True:
|
||||
try:
|
||||
reply = await self.get_user_reply()
|
||||
if force:
|
||||
reply = force
|
||||
force = None
|
||||
else:
|
||||
reply = await self.get_user_reply()
|
||||
self.anonymous = await get_valid(reply)
|
||||
await self.add_vaild(message, f'{"Yes" if self.anonymous else "No"}')
|
||||
break
|
||||
@ -382,7 +398,11 @@ class Poll:
|
||||
|
||||
while True:
|
||||
try:
|
||||
reply = await self.get_user_reply()
|
||||
if force:
|
||||
reply = force
|
||||
force = None
|
||||
else:
|
||||
reply = await self.get_user_reply()
|
||||
self.multiple_choice = await get_valid(reply)
|
||||
await self.add_vaild(message, f'{"Yes" if self.multiple_choice else "No"}')
|
||||
break
|
||||
@ -450,7 +470,11 @@ class Poll:
|
||||
|
||||
while True:
|
||||
try:
|
||||
reply = await self.get_user_reply()
|
||||
if force:
|
||||
reply = force
|
||||
force = None
|
||||
else:
|
||||
reply = await self.get_user_reply()
|
||||
options = await get_valid(reply)
|
||||
self.options_reaction_default = False
|
||||
if isinstance(options, int):
|
||||
@ -527,7 +551,11 @@ class Poll:
|
||||
|
||||
while True:
|
||||
try:
|
||||
reply = await self.get_user_reply()
|
||||
if force:
|
||||
reply = force
|
||||
force = None
|
||||
else:
|
||||
reply = await self.get_user_reply()
|
||||
self.roles = await get_valid(reply, roles)
|
||||
await self.add_vaild(message, f'{", ".join(self.roles)}')
|
||||
break
|
||||
@ -540,43 +568,6 @@ class Poll:
|
||||
except InvalidRoles as e:
|
||||
await self.add_error(message, f'**The following roles are invalid: {e.roles}**')
|
||||
|
||||
# async def set_options_traditional(self, force=None):
|
||||
# '''Currently not used as everything is reaction based'''
|
||||
# if force is not None:
|
||||
# self.options_traditional = force
|
||||
# return
|
||||
# if self.stopped: return
|
||||
# text = """**Next you chose from the possible set of options/answers for your poll.**
|
||||
# Type the corresponding number or type your own options, separated by commas.
|
||||
#
|
||||
# **1** - yes, no
|
||||
# **2** - in favour, against, abstain
|
||||
# **3** - love it, like it, don't care, meh, hate it
|
||||
#
|
||||
# If you write your own options they will be listed and can be voted for.
|
||||
# To use your custom options type them like this:
|
||||
# **apple juice, banana ice cream, kiwi slices**"""
|
||||
# message = await self.wizard_says(text)
|
||||
#
|
||||
# reply = ''
|
||||
# while reply == '' or (reply.split(",").__len__() < 2 and reply not in ['1', '2', '3']) \
|
||||
# or (reply.split(",").__len__() > 99 and reply not in ['1', '2', '3']):
|
||||
# if reply != '':
|
||||
# await self.add_error(message,
|
||||
# '**Invalid entry. Type `1` `2` or `3` or a comma separated list (max. 99 options).**')
|
||||
# reply = await self.get_user_reply()
|
||||
# if self.stopped: break
|
||||
#
|
||||
# if reply == '1':
|
||||
# self.options_traditional = ['yes, no']
|
||||
# elif reply == '2':
|
||||
# self.options_traditional = ['in favour', 'against', 'abstain']
|
||||
# elif reply == '3':
|
||||
# self.options_traditional = ['love it', 'like it', 'don\'t care', 'meh', 'hate it']
|
||||
# else:
|
||||
# self.options_traditional = [r.strip() for r in reply.split(",")]
|
||||
# return self.options_traditional
|
||||
|
||||
async def set_weights(self, force=None):
|
||||
"""Set role weights for the poll."""
|
||||
async def get_valid(in_reply, server_roles):
|
||||
@ -623,7 +614,11 @@ class Poll:
|
||||
|
||||
while True:
|
||||
try:
|
||||
reply = await self.get_user_reply()
|
||||
if force:
|
||||
reply = force
|
||||
force = None
|
||||
else:
|
||||
reply = await self.get_user_reply()
|
||||
w_n = await get_valid(reply, self.server.roles)
|
||||
self.weights_roles = w_n[0]
|
||||
self.weights_numbers = w_n[1]
|
||||
@ -686,7 +681,11 @@ class Poll:
|
||||
|
||||
while True:
|
||||
try:
|
||||
reply = await self.get_user_reply()
|
||||
if force:
|
||||
reply = force
|
||||
force = None
|
||||
else:
|
||||
reply = await self.get_user_reply()
|
||||
dt = await get_valid(reply)
|
||||
self.duration = dt
|
||||
if self.duration == 0:
|
||||
@ -705,7 +704,6 @@ class Poll:
|
||||
def finalize(self):
|
||||
self.time_created = datetime.datetime.utcnow().replace(tzinfo=pytz.utc)
|
||||
|
||||
|
||||
async def to_dict(self):
|
||||
if self.channel is None:
|
||||
cid = 0
|
||||
@ -965,7 +963,7 @@ class Poll:
|
||||
# else:
|
||||
# embed = await self.add_field_custom(name='**Options**', value=', '.join(self.get_options()), embed=embed)
|
||||
|
||||
embed.set_footer(text='bot is in development')
|
||||
# embed.set_footer(text='bot is in development')
|
||||
|
||||
return embed
|
||||
|
||||
@ -994,12 +992,6 @@ class Poll:
|
||||
else:
|
||||
return msg
|
||||
|
||||
# def get_options(self):
|
||||
# if self.reaction:
|
||||
# return self.options_reaction
|
||||
# else:
|
||||
# return self.options_traditional
|
||||
|
||||
def get_duration_with_tz(self):
|
||||
if self.duration == 0:
|
||||
return 0
|
||||
@ -1077,7 +1069,6 @@ class Poll:
|
||||
else:
|
||||
return sum([1 for c in [u for u in self.votes] if option in self.votes[c]['choices']])
|
||||
|
||||
|
||||
async def vote(self, user, option, message):
|
||||
if not await self.is_open():
|
||||
# refresh to show closed poll
|
||||
|
||||
@ -1,9 +1,14 @@
|
||||
import argparse
|
||||
import copy
|
||||
import json
|
||||
import logging
|
||||
import shlex
|
||||
|
||||
import discord
|
||||
|
||||
from discord.ext import commands
|
||||
|
||||
from utils.misc import CustomFormatter
|
||||
from .poll import Poll
|
||||
from utils.paginator import embed_list_paginated
|
||||
from essentials.multi_server import get_server_pre, ask_for_server, ask_for_channel
|
||||
@ -34,14 +39,14 @@ class PollControls:
|
||||
|
||||
async def say_error(self, ctx, error_text, footer_text=None):
|
||||
embed = discord.Embed(title='', description=error_text, colour=SETTINGS.color)
|
||||
embed.set_author(name='Error', icon_url=SETTINGS.title_icon)
|
||||
embed.set_author(name='Error', icon_url=SETTINGS.author_icon)
|
||||
if footer_text is not None:
|
||||
embed.set_footer(text=footer_text)
|
||||
await self.bot.say(embed=embed)
|
||||
|
||||
async def say_embed(self, ctx, say_text='', title='Pollmaster', footer_text=None):
|
||||
embed = discord.Embed(title='', description=say_text, colour=SETTINGS.color)
|
||||
embed.set_author(name=title, icon_url=SETTINGS.title_icon)
|
||||
embed.set_author(name=title, icon_url=SETTINGS.author_icon)
|
||||
if footer_text is not None:
|
||||
embed.set_footer(text=footer_text)
|
||||
await self.bot.say(embed=embed)
|
||||
@ -222,7 +227,7 @@ class PollControls:
|
||||
|
||||
title = f' Listing {short} polls'
|
||||
embed = discord.Embed(title='', description='', colour=SETTINGS.color)
|
||||
embed.set_author(name=title, icon_url=SETTINGS.title_icon)
|
||||
embed.set_author(name=title, icon_url=SETTINGS.author_icon)
|
||||
# await self.bot.say(embed=await self.embed_list_paginated(polls, item_fct, embed))
|
||||
# msg = await self.embed_list_paginated(ctx, polls, item_fct, embed, per_page=8)
|
||||
pre = await get_server_pre(self.bot, server)
|
||||
@ -242,13 +247,76 @@ class PollControls:
|
||||
footer = f'Type {pre}show to display all polls'
|
||||
await self.say_error(ctx, error, footer)
|
||||
|
||||
@commands.command(pass_context=True)
|
||||
async def cmd(self, ctx, *, cmd=None):
|
||||
'''The old, command style way paired with the wizard.'''
|
||||
server = await ask_for_server(self.bot, ctx.message)
|
||||
if not server:
|
||||
return
|
||||
pre = await get_server_pre(self.bot, server)
|
||||
|
||||
# generate the argparser and handle invalid stuff
|
||||
descr = 'Accept poll settings via commandstring. \n\n' \
|
||||
'**Wrap all arguments in quotes like this:** \n' \
|
||||
f'{pre}cmd -question \"What tea do you like?\" -o \"green, black, chai\"\n\n' \
|
||||
'The Order of arguments doesn\'t matter. If an argument is missing, it will use the default value. ' \
|
||||
'If an argument is invalid, the wizard will step in. ' \
|
||||
'If the command string is invalid, you will get this error :)'
|
||||
parser = argparse.ArgumentParser(description=descr, formatter_class=CustomFormatter, add_help=False)
|
||||
parser.add_argument('-question', '-q')
|
||||
parser.add_argument('-label', '-l', default=str(await generate_word(self.bot, server.id)))
|
||||
parser.add_argument('-options', '-o')
|
||||
parser.add_argument('-roles', '-r', default='all')
|
||||
parser.add_argument('-weights', '-w', default='none')
|
||||
parser.add_argument('-duration', '-d', default='0')
|
||||
parser.add_argument('-anonymous', '-a', action="store_true")
|
||||
parser.add_argument('-multiple_choice', '-mc', action="store_true")
|
||||
|
||||
helpstring = parser.format_help()
|
||||
helpstring = helpstring.replace("pollmaster.py", f"{pre}cmd ")
|
||||
|
||||
if cmd and cmd == 'help':
|
||||
await self.say_embed(ctx, say_text=helpstring)
|
||||
return
|
||||
|
||||
try:
|
||||
cmds = shlex.split(cmd)
|
||||
except ValueError:
|
||||
await self.say_error(ctx, error_text=helpstring)
|
||||
return
|
||||
|
||||
try:
|
||||
args = parser.parse_args(cmds)
|
||||
except SystemExit:
|
||||
await self.say_error(ctx, error_text=helpstring)
|
||||
return
|
||||
|
||||
# pass arguments to the wizard
|
||||
async def route(poll):
|
||||
await poll.set_name(force=args.question)
|
||||
await poll.set_short(force=args.label)
|
||||
await poll.set_anonymous(force=f'{"yes" if args.anonymous else "no"}')
|
||||
await poll.set_multiple_choice(force=f'{"yes" if args.multiple_choice else "no"}')
|
||||
await poll.set_options_reaction(force=args.options)
|
||||
await poll.set_roles(force=args.roles)
|
||||
await poll.set_weights(force=args.weights)
|
||||
await poll.set_duration(force=args.duration)
|
||||
|
||||
poll = await self.wizard(ctx, route, server)
|
||||
if poll:
|
||||
await poll.post_embed()
|
||||
|
||||
|
||||
@commands.command(pass_context=True)
|
||||
async def quick(self, ctx, *, cmd=None):
|
||||
'''Create a quick poll with just a question and some options. Parameters: <Question> (optional)'''
|
||||
server = await ask_for_server(self.bot, ctx.message)
|
||||
if not server:
|
||||
return
|
||||
|
||||
async def route(poll):
|
||||
await poll.set_name(force=cmd)
|
||||
await poll.set_short(force=str(await generate_word(self.bot, ctx.message.server.id)))
|
||||
await poll.set_short(force=str(await generate_word(self.bot, server.id)))
|
||||
await poll.set_anonymous(force='no')
|
||||
await poll.set_multiple_choice(force='no')
|
||||
await poll.set_options_reaction()
|
||||
@ -256,13 +324,16 @@ class PollControls:
|
||||
await poll.set_weights(force='none')
|
||||
await poll.set_duration(force='0')
|
||||
|
||||
poll = await self.wizard(ctx, route)
|
||||
poll = await self.wizard(ctx, route, server)
|
||||
if poll:
|
||||
await poll.post_embed()
|
||||
|
||||
@commands.command(pass_context=True)
|
||||
async def prepare(self, ctx, *, cmd=None):
|
||||
'''Prepare a poll to use later. Parameters: <Question> (optional) '''
|
||||
server = await ask_for_server(self.bot, ctx.message)
|
||||
if not server:
|
||||
return
|
||||
|
||||
async def route(poll):
|
||||
await poll.set_name(force=cmd)
|
||||
@ -278,13 +349,16 @@ class PollControls:
|
||||
await poll.set_weights()
|
||||
await poll.set_duration()
|
||||
|
||||
poll = await self.wizard(ctx, route)
|
||||
poll = await self.wizard(ctx, route, server)
|
||||
if poll:
|
||||
await poll.post_embed(destination=ctx.message.author)
|
||||
|
||||
@commands.command(pass_context=True)
|
||||
async def new(self, ctx, *, cmd=None):
|
||||
'''Start the poll wizard to create a new poll step by step. Parameters: <Question> (optional) '''
|
||||
server = await ask_for_server(self.bot, ctx.message)
|
||||
if not server:
|
||||
return
|
||||
|
||||
async def route(poll):
|
||||
await poll.set_name(force=cmd)
|
||||
@ -299,16 +373,12 @@ class PollControls:
|
||||
await poll.set_weights()
|
||||
await poll.set_duration()
|
||||
|
||||
poll = await self.wizard(ctx, route)
|
||||
poll = await self.wizard(ctx, route, server)
|
||||
if poll:
|
||||
await poll.post_embed()
|
||||
|
||||
# The Wizard!
|
||||
async def wizard(self, ctx, route):
|
||||
server = await ask_for_server(self.bot, ctx.message)
|
||||
if not server:
|
||||
return
|
||||
|
||||
async def wizard(self, ctx, route, server):
|
||||
channel = await ask_for_channel(self.bot, server, ctx.message)
|
||||
if not channel:
|
||||
return
|
||||
|
||||
@ -1,6 +1,35 @@
|
||||
import argparse
|
||||
|
||||
import pytz
|
||||
import datetime as dt
|
||||
|
||||
|
||||
class CustomFormatter(argparse.RawTextHelpFormatter):
|
||||
def _format_action_invocation(self, action):
|
||||
if not action.option_strings:
|
||||
metavar, = self._metavar_formatter(action, action.dest)(1)
|
||||
return metavar
|
||||
else:
|
||||
parts = []
|
||||
# if the Optional doesn't take a value, format is:
|
||||
# -s, --long
|
||||
if action.nargs == 0:
|
||||
parts.extend(action.option_strings)
|
||||
|
||||
# if the Optional takes a value, format is:
|
||||
# -s ARGS, --long ARGS
|
||||
# change to
|
||||
# -s, --long ARGS
|
||||
else:
|
||||
default = action.dest.upper()
|
||||
args_string = self._format_args(action, default)
|
||||
for option_string in action.option_strings:
|
||||
# parts.append('%s %s' % (option_string, args_string))
|
||||
parts.append('%s' % option_string)
|
||||
parts[-1] += ' %s' % args_string
|
||||
return ', '.join(parts)
|
||||
|
||||
|
||||
def possible_timezones(tz_offset, common_only=True):
|
||||
# pick one of the timezone collections
|
||||
timezones = pytz.common_timezones if common_only else pytz.all_timezones
|
||||
|
||||
Loading…
Reference in New Issue
Block a user