Compare commits

...
Author SHA1 Message Date
imcompiling da0acb2827 Merge pull request 'Update actions/checkout action to v4' (#72) from renovate/actions-checkout-4.x into main
build_develop / build (push) Successful in 48s
Reviewed-on: #72
2025-02-16 11:25:55 -05:00
renovate-bot 0baffe96f3 Update actions/checkout action to v4 2025-02-16 05:01:09 +00:00
imcompiling 990b7042c4 Add renovatebot json config.
build_develop / build (push) Successful in 49s
2025-02-04 17:38:07 -05:00
imcompiling c977a4e958 Bug fix #64, was using wrong variable.
build_develop / build (push) Successful in 46s
Utils.py got formatted by ruff.
2024-09-30 12:55:34 -04:00
imcompiling e2e8d8de30 Don't need to print the help string.
build_develop / build (push) Successful in 1m20s
build_release / build (push) Successful in 20s
2024-09-29 23:31:49 -04:00
imcompiling 7f007ffa1f Merge commit '02e7a6df3a13bb19056f31f616101980b668ae43'
build_develop / build (push) Successful in 2m20s
2023-08-30 09:04:36 -04:00
imcompiling 913f915bf0 Clarify create category option description. 2023-08-30 09:04:24 -04:00
imcompiling 02e7a6df3a Comment out troublesome code. I believe that this causes users to have trouble submitting multiple in a row over 5 minutes. 2023-08-29 21:01:13 -04:00
imcompiling 7be869b2b6 Update registry location.
build_develop / build (push) Successful in 1m14s
2023-07-29 18:34:56 -04:00
imcompiling 15c4776918 its async. must await.
build_develop / build (push) Failing after 1m29s
2023-07-25 13:38:48 -04:00
imcompiling d3102b57cc Add new birthday action.
build_develop / build (push) Has been cancelled
2023-07-25 11:19:56 -04:00
imcompiling 9bef20de5b Clarify wording in submission process.
build
2023-04-30 21:54:02 -04:00
9 changed files with 144 additions and 39 deletions
+9 -3
View File
@@ -9,12 +9,18 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- name: Checkout Code - name: Checkout Code
uses: actions/checkout@v3 uses: actions/checkout@v4
with: with:
fetch-depth: 0 fetch-depth: 0
- name: Install Docker - name: Install Docker
uses: https://github.com/papodaca/install-docker-action@v1 uses: https://github.com/papodaca/install-docker-action@v1
- name: Log into container registry
uses: docker/login-action@v2
with:
registry: gitea.cheezers.org
username: imcompiling
password: ${{ secrets.PASSWORD }}
- name: Build Docker Image - name: Build Docker Image
run: docker build -t viker.cheezers.net:5000/agon:develop . run: docker build -t gitea.cheezers.org/imcompiling/agon:develop .
- name: Push Docker Image - name: Push Docker Image
run: docker push viker.cheezers.net:5000/agon:develop run: docker push gitea.cheezers.org/imcompiling/agon:develop
+10 -4
View File
@@ -9,16 +9,22 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- name: Checkout Code - name: Checkout Code
uses: actions/checkout@v3 uses: actions/checkout@v4
with: with:
fetch-depth: 0 fetch-depth: 0
- name: Install Docker - name: Install Docker
uses: https://github.com/papodaca/install-docker-action@v1 uses: https://github.com/papodaca/install-docker-action@v1
- name: Log into container registry
uses: docker/login-action@v2
with:
registry: gitea.cheezers.org
username: imcompiling
password: ${{ secrets.PASSWORD }}
- name: Set env - name: Set env
run: echo "GIT_TAG=${GITHUB_REF#refs/*/}" >> $GITHUB_ENV run: echo "GIT_TAG=${GITHUB_REF#refs/*/}" >> $GITHUB_ENV
- name: Build Docker Images - name: Build Docker Images
run: docker build -t viker.cheezers.net:5000/agon:latest -t viker.cheezers.net:5000/agon:${{env.GIT_TAG}} . run: docker build -t gitea.cheezers.org/imcompiling/agon:latest -t gitea.cheezers.org/imcompiling/agon:${{env.GIT_TAG}} .
- name: Push Latest Image - name: Push Latest Image
run: docker push viker.cheezers.net:5000/agon:latest run: docker push gitea.cheezers.org/imcompiling/agon:latest
- name: Push Tagged Image - name: Push Tagged Image
run: docker push viker.cheezers.net:5000/agon:${{env.GIT_TAG}} run: docker push gitea.cheezers.org/imcompiling/agon:${{env.GIT_TAG}}
+5 -3
View File
@@ -183,11 +183,13 @@ class Submission:
if state is SubmissionState.CATEGORY: if state is SubmissionState.CATEGORY:
description = "Step 1: Choose your category!" description = "Step 1: Choose your category!"
elif state is SubmissionState.SCORE: elif state is SubmissionState.SCORE:
description = "Step 2: Input your score!" description = "Step 2: Send a message to input your score!"
elif state is SubmissionState.PROOF: elif state is SubmissionState.PROOF:
description = "Step 3: Submit your proof!" description = "Step 3: Send a message with a picture attached to submit your proof!"
elif state is SubmissionState.NAME: elif state is SubmissionState.NAME:
description = "Step 4 (Optional): Change name on submission! (proceed to next if skipping)" description = (
"Step 4 (Optional): Send a message to change name on submission! (proceed to next if skipping)"
)
elif state is SubmissionState.SUBMIT: elif state is SubmissionState.SUBMIT:
description = "Step 5: Submit if everything looks correct!" description = "Step 5: Submit if everything looks correct!"
elif state is SubmissionState.VERIFY: elif state is SubmissionState.VERIFY:
+1 -1
View File
@@ -40,7 +40,7 @@ class CreateCog(commands.Cog, name="Create Cog"):
interaction: nextcord.Interaction, interaction: nextcord.Interaction,
group_id: str = nextcord.SlashOption(name="group", description="Group to add Category to.", required=True), group_id: str = nextcord.SlashOption(name="group", description="Group to add Category to.", required=True),
category_name: str = nextcord.SlashOption(description="Name of new Category.", required=True), category_name: str = nextcord.SlashOption(description="Name of new Category.", required=True),
is_ascending: bool = nextcord.SlashOption(description="If higher value is better score.", required=True), is_ascending: bool = nextcord.SlashOption(description="If lower value is a better score.", required=True),
is_time_record: bool = nextcord.SlashOption( is_time_record: bool = nextcord.SlashOption(
description="If the score should be shown in time format. Cannot be changed.", required=True description="If the score should be shown in time format. Cannot be changed.", required=True
), ),
-1
View File
@@ -42,6 +42,5 @@ This channel will be where all user submission messages are sent.
3.) Set up your highscore tables! Use "/create group" to first create a group message in the channel you would like and then use "/create category" to create a category in that group message!""" 3.) Set up your highscore tables! Use "/create group" to first create a group message in the channel you would like and then use "/create category" to create a category in that group message!"""
# pylint: enable=line-too-long # pylint: enable=line-too-long
print(help_str)
await interaction.response.send_message(content=help_str) await interaction.response.send_message(content=help_str)
+19 -1
View File
@@ -3,6 +3,7 @@ Defines cog for on message listener.
""" """
import re import re
from datetime import datetime
import nextcord import nextcord
from nextcord.ext import commands from nextcord.ext import commands
@@ -28,6 +29,8 @@ class SubmissionListener(commands.Cog, name="Message Listener"):
if message.author.id == self.bot.user.id: if message.author.id == self.bot.user.id:
return return
await birthday_action(message)
guild_id = message.guild.id guild_id = message.guild.id
if submission_objects.has_user(message.author.id): if submission_objects.has_user(message.author.id):
@@ -45,7 +48,6 @@ class SubmissionListener(commands.Cog, name="Message Listener"):
if message.channel.id == submission_channel_id: if message.channel.id == submission_channel_id:
state = submission.submission_state state = submission.submission_state
if state == SubmissionState.SCORE and message.content: if state == SubmissionState.SCORE and message.content:
stmt = select(Category.IsTimeRecord).where(Category.CategoryId == submission.category_id) stmt = select(Category.IsTimeRecord).where(Category.CategoryId == submission.category_id)
# check with regex if score matches correctly # check with regex if score matches correctly
@@ -102,3 +104,19 @@ class SubmissionListener(commands.Cog, name="Message Listener"):
def setup(bot: commands.Bot): def setup(bot: commands.Bot):
"""Adds function to bot""" """Adds function to bot"""
bot.add_cog(SubmissionListener(bot)) bot.add_cog(SubmissionListener(bot))
async def birthday_action(message: nextcord.Message) -> None:
"""
Does the birthday thing, currently for chris only.
Args:
message (nextcord.Message): The message to check for birthday thing.
"""
today = datetime.today()
birthday = datetime(today.year, 7, 31)
chris = 642330132958281750
if today.date() == birthday.date():
if message.author.id == chris or chris in message.raw_mentions:
await message.add_reaction("🎂")
+3 -3
View File
@@ -231,6 +231,6 @@ class SubmissionView(nextcord.ui.View):
return check return check
async def on_timeout(self) -> None: # async def on_timeout(self) -> None:
# remove user from submission objects after time out. Allows user to start new submission. # # remove user from submission objects after time out. Allows user to start new submission.
submission_objects.remove_user_submission(self._submission_user) # submission_objects.remove_user_submission(self._submission_user)
+19
View File
@@ -0,0 +1,19 @@
{
"$schema": "https://docs.renovatebot.com/renovate-schema.json",
"lockFileMaintenance": {
"automerge": true
},
"minor": {
"automerge": true,
"automergeType": "branch"
},
"patch": {
"automerge": true,
"automergeType": "branch"
},
"pin": {
"automerge": true,
"automergeType": "branch"
},
"ignoreTests": true
}
+78 -23
View File
@@ -16,7 +16,9 @@ from utilities.sql_data_classes import Category, CategoryGroup, Guild, Score, en
MAX_LINE_LENGTH = 142 MAX_LINE_LENGTH = 142
def autofill_categories(guild_id: int, group_id: int, category_begin: str) -> "dict[str, str]": def autofill_categories(
guild_id: int, group_id: int, category_begin: str
) -> "dict[str, str]":
""" """
Returns all category names that start with category_begin. Returns all category names that start with category_begin.
If category_begin is empty, returns list of all category names. If category_begin is empty, returns list of all category names.
@@ -40,16 +42,20 @@ def autofill_categories(guild_id: int, group_id: int, category_begin: str) -> "d
) )
cat_group_alias = aliased(CategoryGroup, subq) cat_group_alias = aliased(CategoryGroup, subq)
stmt = select(Category).where(Category.GroupId == cat_group_alias.GroupId) stmt = select(Category).where(Category.GroupId == cat_group_alias.GroupId)
categories_dict: "dict[str, str]" = {cat.CategoryName: str(cat.CategoryId) for cat in session.scalars(stmt)} categories_dict: "dict[str, str]" = {
cat.CategoryName: str(cat.CategoryId) for cat in session.scalars(stmt)
}
# if string empty, return all category names # if string empty, return all category names
if not category_begin: if not category_begin:
return dict(list(category_begin.items())[:25]) return dict(list(categories_dict.items())[:25])
# else find all categories that start with category_begin # else find all categories that start with category_begin
# TODO is it better to have sql handle the starts with or python? # TODO is it better to have sql handle the starts with or python?
categories: "dict[str, str]" = { categories: "dict[str, str]" = {
cat_name: cat_id for cat_name, cat_id in categories_dict.items() if category_begin.lower() in cat_name.lower() cat_name: cat_id
for cat_name, cat_id in categories_dict.items()
if category_begin.lower() in cat_name.lower()
} }
return dict(list(categories.items())[:25]) return dict(list(categories.items())[:25])
@@ -71,7 +77,9 @@ def autofill_groups(guild_id: int, group_begin: str) -> "dict[str, str]":
stmt = select(CategoryGroup).where(CategoryGroup.GuildId == guild_id) stmt = select(CategoryGroup).where(CategoryGroup.GuildId == guild_id)
# dict has to have key values of same type for discord. # dict has to have key values of same type for discord.
group_dict: "dict[str, str]" = {group.GroupName: str(group.GroupId) for group in session.scalars(stmt)} group_dict: "dict[str, str]" = {
group.GroupName: str(group.GroupId) for group in session.scalars(stmt)
}
# if string empty, return all group names # if string empty, return all group names
if not group_begin: if not group_begin:
@@ -79,13 +87,17 @@ def autofill_groups(guild_id: int, group_begin: str) -> "dict[str, str]":
# else find all groups that start with group_begin # else find all groups that start with group_begin
groups: "dict[str, str]" = { groups: "dict[str, str]" = {
group_name: group_id for group_name, group_id in group_dict.items() if group_begin.lower() in group_name.lower() group_name: group_id
for group_name, group_id in group_dict.items()
if group_begin.lower() in group_name.lower()
} }
return dict(list(groups.items())[:25]) return dict(list(groups.items())[:25])
def autofill_users_in_group_category(guild_id: int, group_id: int, category_id: int, user_begin: str) -> "list[str]": def autofill_users_in_group_category(
guild_id: int, group_id: int, category_id: int, user_begin: str
) -> "list[str]":
""" """
Returns list of users that match user_begin. Either all users in group or just users in category if category is Returns list of users that match user_begin. Either all users in group or just users in category if category is
not None. Might be expensive due to unioning all users in group. not None. Might be expensive due to unioning all users in group.
@@ -112,7 +124,9 @@ def autofill_users_in_group_category(guild_id: int, group_id: int, category_id:
# If no category id, get all users in group. # If no category id, get all users in group.
if category_id == 0: if category_id == 0:
subq = select(Category.CategoryId).where(Category.GroupId == category_group.GroupId) subq = select(Category.CategoryId).where(
Category.GroupId == category_group.GroupId
)
stmt = select(distinct(Score.UserName)).where(Score.CategoryId.in_(subq)) stmt = select(distinct(Score.UserName)).where(Score.CategoryId.in_(subq))
else: else:
@@ -124,7 +138,9 @@ def autofill_users_in_group_category(guild_id: int, group_id: int, category_id:
.subquery() .subquery()
) )
category = aliased(Category, subq) category = aliased(Category, subq)
stmt = select(distinct(Score.UserName)).where(Score.CategoryId == category.CategoryId) stmt = select(distinct(Score.UserName)).where(
Score.CategoryId == category.CategoryId
)
users_list: "list[str]" = list(session.scalars(stmt)) users_list: "list[str]" = list(session.scalars(stmt))
@@ -133,7 +149,9 @@ def autofill_users_in_group_category(guild_id: int, group_id: int, category_id:
return users_list[:25] return users_list[:25]
# else find all users that start with user_begin # else find all users that start with user_begin
users: "list[str]" = [user for user in users_list if user_begin.lower() in user.lower()] users: "list[str]" = [
user for user in users_list if user_begin.lower() in user.lower()
]
return users[:25] return users[:25]
@@ -151,9 +169,15 @@ def autofill_users_in_guild(guild_id: int, user_begin: str) -> "list[str]":
""" """
with Session(engine) as session: with Session(engine) as session:
group_ids = select(CategoryGroup.GroupId).where(CategoryGroup.GuildId == guild_id) group_ids = select(CategoryGroup.GroupId).where(
category_ids = select(Category.CategoryId).where(Category.GroupId.in_(group_ids)) CategoryGroup.GuildId == guild_id
stmt = select(distinct(Score.UserName)).where(Score.CategoryId.in_(category_ids)) )
category_ids = select(Category.CategoryId).where(
Category.GroupId.in_(group_ids)
)
stmt = select(distinct(Score.UserName)).where(
Score.CategoryId.in_(category_ids)
)
users_list: "list[str]" = list(session.scalars(stmt)) users_list: "list[str]" = list(session.scalars(stmt))
# if string empty, return all users # if string empty, return all users
@@ -161,7 +185,9 @@ def autofill_users_in_guild(guild_id: int, user_begin: str) -> "list[str]":
return users_list[:25] return users_list[:25]
# else find all users that start with user_begin # else find all users that start with user_begin
users: "list[str]" = [user for user in users_list if user_begin.lower() in user.lower()] users: "list[str]" = [
user for user in users_list if user_begin.lower() in user.lower()
]
return users[:25] return users[:25]
@@ -207,7 +233,10 @@ def format_highscore_message(session: Session, group: CategoryGroup) -> str:
category_ids.append(cat.CategoryId) category_ids.append(cat.CategoryId)
# get all scores in category group, load into data frame. # get all scores in category group, load into data frame.
d_f = pd.read_sql_query(sql=session.query(Score).where(Score.CategoryId.in_(category_ids)).statement, con=engine) d_f = pd.read_sql_query(
sql=session.query(Score).where(Score.CategoryId.in_(category_ids)).statement,
con=engine,
)
# this list is what will be printed in the discord message # this list is what will be printed in the discord message
# first string will be category list, others will be score printouts # first string will be category list, others will be score printouts
@@ -225,17 +254,26 @@ def format_highscore_message(session: Session, group: CategoryGroup) -> str:
# process data. Want each group sorted correctly and only top X results # process data. Want each group sorted correctly and only top X results
processed_group = ( processed_group = (
group_df.sort_values("Score", ascending=category.IsAscending).head(category.Size).reset_index() group_df.sort_values("Score", ascending=category.IsAscending)
.head(category.Size)
.reset_index()
) )
# add each score to list # add each score to list
for ind in range(max_cat_size): # need to subtract to deal with category name string for ind in range(
max_cat_size
): # need to subtract to deal with category name string
if ind in processed_group.index: if ind in processed_group.index:
username = processed_group["UserName"][ind] username = processed_group["UserName"][ind]
score = processed_group["Score"][ind] score = processed_group["Score"][ind]
str_list[ind + 1] += format_score_string( str_list[ind + 1] += format_score_string(
username, score, group.UsernameLength, category.IsTimeRecord, ind + 1, pad_length username,
score,
group.UsernameLength,
category.IsTimeRecord,
ind + 1,
pad_length,
) )
else: else:
# if not enough entries, pad out # if not enough entries, pad out
@@ -275,7 +313,12 @@ def format_highscore_message(session: Session, group: CategoryGroup) -> str:
def format_score_string( def format_score_string(
username: str, score: float, username_length: int, is_time_record: bool, rank: int, pad_length: int username: str,
score: float,
username_length: int,
is_time_record: bool,
rank: int,
pad_length: int,
) -> str: ) -> str:
""" """
Builds the string to show a user's score. Builds the string to show a user's score.
@@ -321,7 +364,9 @@ def get_time_str(time_in: float) -> str:
return time.strftime(f"%-M:%S.{milliseconds}", time.gmtime(time_in)) return time.strftime(f"%-M:%S.{milliseconds}", time.gmtime(time_in))
async def send_highscore_message(session: Session, guild: nextcord.Guild, group: CategoryGroup) -> nextcord.Message: async def send_highscore_message(
session: Session, guild: nextcord.Guild, group: CategoryGroup
) -> nextcord.Message:
""" """
Function takes care of checking if a message exists for a group. Function takes care of checking if a message exists for a group.
Creates and sends/edits the message. Creates and sends/edits the message.
@@ -351,7 +396,11 @@ async def send_highscore_message(session: Session, guild: nextcord.Guild, group:
async def submit_score( async def submit_score(
interaction: nextcord.Interaction, group_id: int, category_id: int, username: str, score: str interaction: nextcord.Interaction,
group_id: int,
category_id: int,
username: str,
score: str,
) -> None: ) -> None:
""" """
Adds passed score to group. Then updates group message by calling send_highscore_message. Adds passed score to group. Then updates group message by calling send_highscore_message.
@@ -376,7 +425,11 @@ async def submit_score(
else: else:
score = float(score) score = float(score)
stmt = select(Score).where(Score.UserName == username).where(Score.CategoryId == category_id) stmt = (
select(Score)
.where(Score.UserName == username)
.where(Score.CategoryId == category_id)
)
existing_score = session.scalar(stmt) existing_score = session.scalar(stmt)
if existing_score: if existing_score:
@@ -403,7 +456,9 @@ def add_preset_configuration(guild_id: int, config_str: str) -> None:
""" """
with Session(engine) as session: with Session(engine) as session:
with open(f"example_config/{config_str}.json", encoding="utf-8", mode="r") as file: with open(
f"example_config/{config_str}.json", encoding="utf-8", mode="r"
) as file:
config = json.load(file) config = json.load(file)
for group_name, categorys in config["tables"].items(): for group_name, categorys in config["tables"].items():