From 25226a460bd3347a618d80af2f598d3969a8a7a2 Mon Sep 17 00:00:00 2001 From: ComputerTech312 Date: Fri, 26 Sep 2025 19:13:52 +0100 Subject: [PATCH] Fix magazine and bullet usage limits - Fixed bug where players could use magazines beyond their level's maximum limit - Added validation to prevent using bullets when magazine is already full - Magazine items now respect level-based limits (e.g., 3 magazines at level 1) - Items are not consumed from inventory if they can't be used due to limits - Added proper error messages for when limits are reached - Updated ShopManager to work with LevelManager for limit validation --- duckhunt.json | 24 +++++- logs/duckhunt.log | 90 ++++++++++++++++++++ src/__pycache__/duckhuntbot.cpython-312.pyc | Bin 61544 -> 61572 bytes src/__pycache__/game.cpython-312.pyc | Bin 22970 -> 22999 bytes src/__pycache__/shop.cpython-312.pyc | Bin 19829 -> 21003 bytes src/duckhuntbot.py | 10 +-- src/shop.py | 46 +++++++++- 7 files changed, 157 insertions(+), 13 deletions(-) diff --git a/duckhunt.json b/duckhunt.json index 3e041b9..087b05b 100644 --- a/duckhunt.json +++ b/duckhunt.json @@ -1,8 +1,8 @@ { "players": { "computertech": { - "nick": "computertech", - "xp": 67, + "nick": "ComputerTech", + "xp": 2, "ducks_shot": 6, "ducks_befriended": 2, "shots_fired": 2, @@ -10,14 +10,30 @@ "accuracy": 63, "gun_confiscated": false, "current_ammo": 6, - "magazines": 3, + "magazines": 7, "bullets_per_magazine": 6, "jam_chance": 5, "inventory": { "1": 1 }, "temporary_effects": [] + }, + "seokly": { + "nick": "seokly", + "xp": 0, + "ducks_shot": 0, + "ducks_befriended": 0, + "shots_fired": 0, + "shots_missed": 0, + "accuracy": 75, + "gun_confiscated": false, + "current_ammo": 6, + "magazines": 3, + "bullets_per_magazine": 6, + "jam_chance": 15, + "inventory": {}, + "temporary_effects": [] } }, - "last_save": "1758909688.9995604" + "last_save": "1758910394.7242796" } \ No newline at end of file diff --git a/logs/duckhunt.log b/logs/duckhunt.log index 1ab517b..5e1ff9f 100644 --- a/logs/duckhunt.log +++ b/logs/duckhunt.log @@ -410,3 +410,93 @@ 19:04:05.573 📘 INFO DuckHuntBot.Game Normal duck spawned in #ct 19:05:15.648 📘 INFO DuckHuntBot.Game Fast duck (hidden) spawned in #ct 19:05:39.670 📘 INFO DuckHuntBot.Game Normal duck spawned in #ct +19:06:48.726 📘 INFO DuckHuntBot.Game Normal duck spawned in #ct +19:06:49.141 📘 INFO DuckHuntBot 🛑 Received SIGINT (Ctrl+C), shutting down immediately... +19:06:49.151 📘 INFO DuckHuntBot 🔄 Cancelled 5 running tasks +19:06:49.158 📘 INFO DuckHuntBot Message loop cancelled +19:06:49.159 📘 INFO DuckHuntBot Message loop ended +19:06:49.159 📘 INFO DuckHuntBot 🛑 Main loop cancelled +19:06:49.160 📘 INFO DuckHuntBot.Game Duck spawning loop cancelled +19:06:49.161 📘 INFO DuckHuntBot.Game Duck timeout loop cancelled +19:06:49.161 📘 INFO DuckHuntBot.Game Game loops cancelled +19:06:49.185 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:06:49.186 📘 INFO DuckHuntBot 💾 Database saved +19:06:49.398 📘 INFO DuckHuntBot 🔌 IRC connection closed +19:06:49.399 📘 INFO DuckHuntBot ✅ Bot shutdown complete +19:06:57.707 📘 INFO DuckHuntBot Unified logging system initialized: all logs in duckhunt.log +19:06:57.707 📘 INFO DuckHuntBot Debug mode: ON +19:06:57.707 📘 INFO DuckHuntBot Log everything: YES +19:06:57.707 📘 INFO DuckHuntBot Unified format: YES +19:06:57.707 📘 INFO DuckHuntBot Console level: INFO +19:06:57.707 📘 INFO DuckHuntBot File level: DEBUG +19:06:57.708 📘 INFO DuckHuntBot Main log: /home/colby/duckhunt/logs/duckhunt.log +19:06:57.708 📘 INFO DuckHuntBot 🤖 Initializing DuckHunt Bot components... +19:06:57.708 📘 INFO DuckHuntBot.DB Loaded 1 players from duckhunt.json +19:06:57.715 📘 INFO SASL Unified logging system initialized: all logs in duckhunt.log +19:06:57.715 📘 INFO SASL Debug mode: ON +19:06:57.716 📘 INFO SASL Log everything: YES +19:06:57.716 📘 INFO SASL Unified format: YES +19:06:57.717 📘 INFO SASL Console level: INFO +19:06:57.717 📘 INFO SASL File level: DEBUG +19:06:57.717 📘 INFO SASL Main log: /home/colby/duckhunt/logs/duckhunt.log +19:06:57.717 📘 INFO DuckHuntBot 👑 Configured 3 admin(s): peorth, computertech, colby +19:06:57.718 📘 INFO DuckHuntBot.Shop Loaded 9 shop items from /home/colby/duckhunt/shop.json +19:06:57.718 📘 INFO DuckHuntBot.Levels Loaded 8 levels from /home/colby/duckhunt/levels.json +19:06:57.719 📘 INFO DuckHuntBot 🦆 Starting DuckHunt Bot... +19:06:57.767 📘 INFO DuckHuntBot Attempting to connect to irc.rizon.net:6697 (attempt 1/3) +19:06:57.944 📘 INFO DuckHuntBot ✅ Successfully connected to irc.rizon.net:6697 +19:06:57.944 📘 INFO DuckHuntBot 🔐 Sending server password +19:06:57.945 📘 INFO DuckHuntBot 🦆 Bot is now running! Press Ctrl+C to stop. +19:06:59.122 📘 INFO DuckHuntBot Successfully registered with IRC server +19:07:02.131 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:07:10.467 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:07:12.307 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:07:29.690 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:07:32.598 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:07:39.223 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:07:41.056 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:07:45.298 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:07:46.350 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 1 players [save_database:142] +19:12:52.027 📘 INFO DuckHuntBot 🛑 Received SIGINT (Ctrl+C), shutting down immediately... +19:12:52.066 📘 INFO DuckHuntBot 🔄 Cancelled 5 running tasks +19:12:51.888 📘 INFO DuckHuntBot 🛑 Received SIGINT (Ctrl+C), shutting down immediately... +19:12:52.067 📘 INFO DuckHuntBot 🔄 Cancelled 5 running tasks +19:12:52.069 📘 INFO DuckHuntBot Message loop cancelled +19:12:52.071 📘 INFO DuckHuntBot Message loop ended +19:12:52.080 📘 INFO DuckHuntBot.Game Duck spawning loop cancelled +19:12:52.082 📘 INFO DuckHuntBot.Game Duck timeout loop cancelled +19:12:52.082 📘 INFO DuckHuntBot 🛑 Main loop cancelled +19:12:52.085 📘 INFO DuckHuntBot.Game Game loops cancelled +19:12:52.306 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 2 players [save_database:142] +19:12:52.309 📘 INFO DuckHuntBot 💾 Database saved +19:12:53.133 📘 INFO DuckHuntBot 🔌 IRC connection closed +19:12:53.136 📘 INFO DuckHuntBot ✅ Bot shutdown complete +19:12:53.597 📘 INFO DuckHuntBot Unified logging system initialized: all logs in duckhunt.log +19:12:53.597 📘 INFO DuckHuntBot Debug mode: ON +19:12:53.597 📘 INFO DuckHuntBot Log everything: YES +19:12:53.598 📘 INFO DuckHuntBot Unified format: YES +19:12:53.598 📘 INFO DuckHuntBot Console level: INFO +19:12:53.598 📘 INFO DuckHuntBot File level: DEBUG +19:12:53.598 📘 INFO DuckHuntBot Main log: /home/colby/duckhunt/logs/duckhunt.log +19:12:53.598 📘 INFO DuckHuntBot 🤖 Initializing DuckHunt Bot components... +19:12:53.599 📘 INFO DuckHuntBot.DB Loaded 2 players from duckhunt.json +19:12:53.605 📘 INFO SASL Unified logging system initialized: all logs in duckhunt.log +19:12:53.606 📘 INFO SASL Debug mode: ON +19:12:53.606 📘 INFO SASL Log everything: YES +19:12:53.606 📘 INFO SASL Unified format: YES +19:12:53.606 📘 INFO SASL Console level: INFO +19:12:53.606 📘 INFO SASL File level: DEBUG +19:12:53.606 📘 INFO SASL Main log: /home/colby/duckhunt/logs/duckhunt.log +19:12:53.607 📘 INFO DuckHuntBot 👑 Configured 3 admin(s): peorth, computertech, colby +19:12:53.607 📘 INFO DuckHuntBot.Levels Loaded 8 levels from /home/colby/duckhunt/levels.json +19:12:53.608 📘 INFO DuckHuntBot.Shop Loaded 9 shop items from /home/colby/duckhunt/shop.json +19:12:53.608 📘 INFO DuckHuntBot 🦆 Starting DuckHunt Bot... +19:12:53.660 📘 INFO DuckHuntBot Attempting to connect to irc.rizon.net:6697 (attempt 1/3) +19:12:53.826 📘 INFO DuckHuntBot ✅ Successfully connected to irc.rizon.net:6697 +19:12:53.826 📘 INFO DuckHuntBot 🔐 Sending server password +19:12:53.827 📘 INFO DuckHuntBot 🦆 Bot is now running! Press Ctrl+C to stop. +19:12:55.118 📘 INFO DuckHuntBot Successfully registered with IRC server +19:13:06.811 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 2 players [save_database:142] +19:13:10.747 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 2 players [save_database:142] +19:13:13.374 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 2 players [save_database:142] +19:13:14.741 🔍 DEBUG DuckHuntBot.DB Database saved successfully with 2 players [save_database:142] diff --git a/src/__pycache__/duckhuntbot.cpython-312.pyc b/src/__pycache__/duckhuntbot.cpython-312.pyc index eb38a1b953b874c8c672c43fd2a7056355785ccf..5475b54f6f9ef8eb6398df1c6020eb8c4d5a383d 100644 GIT binary patch delta 245 zcmaFyfVt%%Gw*3$UM>b8aK3&mIqL?z|1vy6I+iE zcTQ?qYEH3UR&jn_6=!iqe!=7b_WR;IK+U(9x<%V{dR!eqVmO6$ua<{d1(oIgJaGl<(4vjL4d%qH$3wKDo=Ei8T`M^6J SMs6*jDPUI>X-@wBz7PP}Jx~?^ delta 229 zcmZp9$o%2~Gw*3$UM>b8Sb61I#;%RLeN2oRo98fbvoNh@oV=fHst{*!Mt*@_R&jn_ z6?aZ*S!z!4tl4C401Y(QfUvx$4~Z!Y9|=FX_OIU-0^0!Yh*ve&w6=TAeA|1H#ei!X4Mtj+!zfu-+8CQ$gK%9r3mD>BCW~79|{3% Cj7m%Z diff --git a/src/__pycache__/game.cpython-312.pyc b/src/__pycache__/game.cpython-312.pyc index f58a32e292b554cc1427ea31de6c28bf8ad5bc4d..e41054418dac0f863609733fc3324c5fb73d8c00 100644 GIT binary patch delta 350 zcmdnBneqB&M&8rByj%=GaNz2-jINEm7xV4^V0Pu-`6|J)(TWo z)INEYzBOa}=4bkj>};+FO0V$yZq_wl%x-W?s3L?_zGq^bJ^8P{24nALwSbu*&Ve8Y##x&ggXc0c&e%LZ ejEhNrEy$pKAmTKL06SM6#OehRvnHR2_yhpuFlsyi delta 338 zcmcb_vPa;RFz& z4;-wS M9uP5m^3#Y<06dLelmGw# diff --git a/src/__pycache__/shop.cpython-312.pyc b/src/__pycache__/shop.cpython-312.pyc index df02ded9ecec8313d3e6dd92bad322e638f1f8ee..0622191e2b804fa773a3c0dcb0841aff228463dc 100644 GIT binary patch delta 5569 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 delta 4544 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 bJC$Lxlc|mTZ?HVP#_@njQa;iU6oLO22EfU^ diff --git a/src/duckhuntbot.py b/src/duckhuntbot.py index b628030..cc42370 100644 --- a/src/duckhuntbot.py +++ b/src/duckhuntbot.py @@ -38,14 +38,14 @@ class DuckHuntBot: self.admins = [admin.lower() for admin in admins_list] self.logger.info(f"👑 Configured {len(self.admins)} admin(s): {', '.join(self.admins)}") - # Initialize shop manager - shop_file = os.path.join(os.path.dirname(os.path.dirname(__file__)), 'shop.json') - self.shop = ShopManager(shop_file) - - # Initialize level manager + # Initialize level manager first levels_file = os.path.join(os.path.dirname(os.path.dirname(__file__)), 'levels.json') self.levels = LevelManager(levels_file) + # Initialize shop manager with levels reference + shop_file = os.path.join(os.path.dirname(os.path.dirname(__file__)), 'shop.json') + self.shop = ShopManager(shop_file, self.levels) + def get_config(self, path, default=None): """Get configuration value using dot notation""" keys = path.split('.') diff --git a/src/shop.py b/src/shop.py index 9c0cf62..3eb1938 100644 --- a/src/shop.py +++ b/src/shop.py @@ -13,8 +13,9 @@ from typing import Dict, Any, Optional class ShopManager: """Manages the DuckHunt shop system""" - def __init__(self, shop_file: str = "shop.json"): + def __init__(self, shop_file: str = "shop.json", levels_manager=None): self.shop_file = shop_file + self.levels = levels_manager self.items = {} self.logger = logging.getLogger('DuckHuntBot.Shop') self.load_items() @@ -198,13 +199,23 @@ class ShopManager: } elif item_type == 'magazine': - # Add magazines to player's inventory + # Add magazines (limit checking is done before this function is called) current_magazines = player.get('magazines', 1) - new_magazines = current_magazines + amount + + if self.levels: + level_info = self.levels.get_player_level_info(player) + max_magazines = level_info.get('magazines', 3) + # Don't exceed maximum magazines for level + magazines_to_add = min(amount, max_magazines - current_magazines) + else: + # Fallback if levels not available + magazines_to_add = amount + + new_magazines = current_magazines + magazines_to_add player['magazines'] = new_magazines return { "type": "magazine", - "added": amount, + "added": magazines_to_add, "new_total": new_magazines } @@ -520,6 +531,33 @@ class ShopManager: "item_name": item['name'] } + # Special checks for ammo/magazine limits + if item['type'] == 'magazine' and self.levels: + affected_player = target_player if target_player else player + current_magazines = affected_player.get('magazines', 1) + level_info = self.levels.get_player_level_info(affected_player) + max_magazines = level_info.get('magazines', 3) + + if current_magazines >= max_magazines: + return { + "success": False, + "error": "max_magazines_reached", + "message": f"Already at maximum magazines ({max_magazines}) for current level!", + "item_name": item['name'] + } + elif item['type'] == 'ammo': + affected_player = target_player if target_player else player + current_ammo = affected_player.get('current_ammo', 0) + bullets_per_mag = affected_player.get('bullets_per_magazine', 6) + + if current_ammo >= bullets_per_mag: + return { + "success": False, + "error": "magazine_full", + "message": f"Current magazine is already full ({bullets_per_mag}/{bullets_per_mag})!", + "item_name": item['name'] + } + # Remove item from inventory inventory[item_id_str] -= 1 if inventory[item_id_str] <= 0: