Skip to content

Commit 79ff946

Browse files
konardclaude
andcommitted
Implement daily message limiting based on karma levels
* Add daily message count tracking to user data model * Create message limit function based on karma thresholds: - No limit for karma > -10 - 64 messages for karma ≤ -10 and > -20 - 32 messages for karma ≤ -20 and > -40 - 16 messages for karma ≤ -40 and > -80 - 8 messages for karma ≤ -80 and > -160 - 4 messages for karma ≤ -160 and > -320 - 2 messages for karma ≤ -320 and > -640 - 1 message for karma ≤ -640 and > -1280 - Read-only mode (0 messages) for karma ≤ -1280 * Add message limiting logic to main bot handler * Include comprehensive test suite Fixes #17 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <[email protected]>
1 parent 03f0d45 commit 79ff946

File tree

5 files changed

+208
-0
lines changed

5 files changed

+208
-0
lines changed

experiments/test_message_limits.py

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
#!/usr/bin/env python3
2+
# -*- coding: utf-8 -*-
3+
"""Test script for message limiting functionality"""
4+
5+
import sys
6+
import os
7+
sys.path.append(os.path.join(os.path.dirname(__file__), '..', 'python'))
8+
9+
from modules.utils import get_daily_message_limit
10+
11+
def test_message_limits():
12+
"""Test the daily message limit function"""
13+
14+
# Test cases based on the issue requirements
15+
test_cases = [
16+
# (karma, expected_limit)
17+
(0, -1), # No limit for karma >= -10
18+
(-5, -1), # No limit for karma >= -10
19+
(-10, 64), # 64 messages for karma < -10 and >= -20
20+
(-15, 64), # 64 messages for karma < -10 and >= -20
21+
(-20, 32), # 32 messages for karma < -20 and >= -40
22+
(-30, 32), # 32 messages for karma < -20 and >= -40
23+
(-40, 16), # 16 messages for karma < -40 and >= -80
24+
(-60, 16), # 16 messages for karma < -40 and >= -80
25+
(-80, 8), # 8 messages for karma < -80 and >= -160
26+
(-120, 8), # 8 messages for karma < -80 and >= -160
27+
(-160, 4), # 4 messages for karma < -160 and >= -320
28+
(-240, 4), # 4 messages for karma < -160 and >= -320
29+
(-320, 2), # 2 messages for karma < -320 and >= -640
30+
(-480, 2), # 2 messages for karma < -320 and >= -640
31+
(-640, 1), # 1 message for karma < -640 and >= -1280
32+
(-960, 1), # 1 message for karma < -640 and >= -1280
33+
(-1280, 0), # Read-only mode for karma < -1280
34+
(-2000, 0), # Read-only mode for karma < -1280
35+
]
36+
37+
print("Testing daily message limits based on karma:")
38+
print("=" * 50)
39+
40+
all_passed = True
41+
for karma, expected_limit in test_cases:
42+
actual_limit = get_daily_message_limit(karma)
43+
status = "✓ PASS" if actual_limit == expected_limit else "✗ FAIL"
44+
45+
if actual_limit != expected_limit:
46+
all_passed = False
47+
48+
print(f"Karma: {karma:5d} | Expected: {expected_limit:3d} | Got: {actual_limit:3d} | {status}")
49+
50+
print("=" * 50)
51+
if all_passed:
52+
print("🎉 All tests passed!")
53+
else:
54+
print("❌ Some tests failed!")
55+
56+
return all_passed
57+
58+
if __name__ == "__main__":
59+
test_message_limits()
Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
#!/usr/bin/env python3
2+
"""Standalone test for message limiting logic"""
3+
4+
def get_daily_message_limit(karma: int) -> int:
5+
"""Returns daily message limit based on karma level.
6+
7+
:param karma: user's karma value
8+
:return: maximum number of messages allowed per day
9+
"""
10+
if karma > -10:
11+
return -1 # No limit
12+
elif karma > -20:
13+
return 64
14+
elif karma > -40:
15+
return 32
16+
elif karma > -80:
17+
return 16
18+
elif karma > -160:
19+
return 8
20+
elif karma > -320:
21+
return 4
22+
elif karma > -640:
23+
return 2
24+
elif karma > -1280:
25+
return 1
26+
else:
27+
return 0 # Read-only mode
28+
29+
30+
def test_message_limits():
31+
"""Test the daily message limit function"""
32+
33+
# Test cases based on the issue requirements
34+
test_cases = [
35+
# (karma, expected_limit)
36+
(0, -1), # No limit for karma > -10
37+
(-5, -1), # No limit for karma > -10
38+
(-9, -1), # No limit for karma > -10
39+
(-10, 64), # 64 messages for karma < -10 and >= -20
40+
(-15, 64), # 64 messages for karma < -10 and >= -20
41+
(-19, 64), # 64 messages for karma < -10 and >= -20
42+
(-20, 32), # 32 messages for karma < -20 and >= -40
43+
(-30, 32), # 32 messages for karma < -20 and >= -40
44+
(-39, 32), # 32 messages for karma < -20 and >= -40
45+
(-40, 16), # 16 messages for karma < -40 and >= -80
46+
(-60, 16), # 16 messages for karma < -40 and >= -80
47+
(-79, 16), # 16 messages for karma < -40 and >= -80
48+
(-80, 8), # 8 messages for karma < -80 and >= -160
49+
(-120, 8), # 8 messages for karma < -80 and >= -160
50+
(-159, 8), # 8 messages for karma < -80 and >= -160
51+
(-160, 4), # 4 messages for karma < -160 and >= -320
52+
(-240, 4), # 4 messages for karma < -160 and >= -320
53+
(-319, 4), # 4 messages for karma < -160 and >= -320
54+
(-320, 2), # 2 messages for karma < -320 and >= -640
55+
(-480, 2), # 2 messages for karma < -320 and >= -640
56+
(-639, 2), # 2 messages for karma < -320 and >= -640
57+
(-640, 1), # 1 message for karma < -640 and >= -1280
58+
(-960, 1), # 1 message for karma < -640 and >= -1280
59+
(-1279, 1), # 1 message for karma < -640 and >= -1280
60+
(-1280, 0), # Read-only mode for karma < -1280
61+
(-2000, 0), # Read-only mode for karma < -1280
62+
]
63+
64+
print("Testing daily message limits based on karma:")
65+
print("=" * 50)
66+
67+
all_passed = True
68+
for karma, expected_limit in test_cases:
69+
actual_limit = get_daily_message_limit(karma)
70+
status = "✓ PASS" if actual_limit == expected_limit else "✗ FAIL"
71+
72+
if actual_limit != expected_limit:
73+
all_passed = False
74+
75+
print(f"Karma: {karma:5d} | Expected: {expected_limit:3d} | Got: {actual_limit:3d} | {status}")
76+
77+
print("=" * 50)
78+
if all_passed:
79+
print("🎉 All tests passed!")
80+
else:
81+
print("❌ Some tests failed!")
82+
83+
return all_passed
84+
85+
if __name__ == "__main__":
86+
test_message_limits()

python/__main__.py

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
from modules import (
1111
BetterBotBaseDataService, Commands
1212
)
13+
from modules.utils import get_daily_message_limit
1314
from tokens import BOT_TOKEN
1415
from userbot import UserBot
1516
import patterns
@@ -99,6 +100,40 @@ def message_new(
99100

100101
user = self.data.get_user(from_id, self) if from_id > 0 else None
101102

103+
# Check daily message limit for users with negative karma
104+
if user and peer_id >= CHAT_ID_OFFSET: # Only apply limits in group chats
105+
current_date = datetime.now().strftime("%Y-%m-%d")
106+
107+
# Reset daily message count if it's a new day
108+
if user.last_message_date != current_date:
109+
user.daily_message_count = 0
110+
user.last_message_date = current_date
111+
self.data.save_user(user)
112+
113+
# Check if user has exceeded their daily message limit
114+
daily_limit = get_daily_message_limit(user.karma)
115+
if daily_limit >= 0: # -1 means no limit
116+
if user.daily_message_count >= daily_limit:
117+
if daily_limit == 0:
118+
# Read-only mode - delete message and notify
119+
self.delete_message(peer_id, msg_id, 0)
120+
self.send_msg(
121+
f"[id{from_id}|Пользователь] находится в режиме только для чтения (карма < -1280).",
122+
peer_id
123+
)
124+
else:
125+
# Message limit exceeded - delete message and notify
126+
self.delete_message(peer_id, msg_id, 0)
127+
self.send_msg(
128+
f"[id{from_id}|Пользователь] превысил лимит сообщений на день ({daily_limit} сообщений). Текущая карма: {user.karma}",
129+
peer_id
130+
)
131+
return
132+
else:
133+
# Increment message count for this day
134+
user.daily_message_count += 1
135+
self.data.save_user(user)
136+
102137
messages = self.get_messages(event)
103138
selected_message = messages[0] if len(messages) == 1 else None
104139
selected_user = (

python/modules/data_service.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@ def __init__(self, db_name: str = "users"):
1919
self.base.addPattern("supporters", [])
2020
self.base.addPattern("opponents", [])
2121
self.base.addPattern("karma", 0)
22+
self.base.addPattern("daily_message_count", 0)
23+
self.base.addPattern("last_message_date", "")
2224

2325
def get_or_create_user(
2426
self,

python/modules/utils.py

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,3 +68,29 @@ def is_available_ghpage(
6868
"""Returns True if github profile is available.
6969
"""
7070
return requests.get(f'https://github.com/{profile}').status_code == 200
71+
72+
73+
def get_daily_message_limit(karma: int) -> int:
74+
"""Returns daily message limit based on karma level.
75+
76+
:param karma: user's karma value
77+
:return: maximum number of messages allowed per day
78+
"""
79+
if karma > -10:
80+
return -1 # No limit
81+
elif karma > -20:
82+
return 64
83+
elif karma > -40:
84+
return 32
85+
elif karma > -80:
86+
return 16
87+
elif karma > -160:
88+
return 8
89+
elif karma > -320:
90+
return 4
91+
elif karma > -640:
92+
return 2
93+
elif karma > -1280:
94+
return 1
95+
else:
96+
return 0 # Read-only mode

0 commit comments

Comments
 (0)