Skip to content

Commit a1cb452

Browse files
committed
Add coverage of regex_chans db access
1 parent e08663a commit a1cb452

File tree

2 files changed

+141
-40
lines changed

2 files changed

+141
-40
lines changed

plugins/core/regex_chans.py

Lines changed: 51 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -15,11 +15,14 @@
1515
UniqueConstraint("connection", "channel"),
1616
)
1717

18+
ENABLED = "ENABLED"
19+
DISABLED = "DISABLED"
20+
1821
# Default value.
1922
# If True, all channels without a setting will have regex enabled
2023
# If False, all channels without a setting will have regex disabled
2124
default_enabled = True
22-
status_cache: Dict[Tuple[str, str], str] = {}
25+
status_cache: Dict[Tuple[str, str], bool] = {}
2326
logger = logging.getLogger("cloudbot")
2427

2528

@@ -30,27 +33,44 @@ def load_cache(db):
3033
conn = row["connection"]
3134
chan = row["channel"]
3235
status = row["status"]
33-
new_cache[(conn, chan)] = status
36+
if status == ENABLED:
37+
value = True
38+
elif status == DISABLED:
39+
value = False
40+
else:
41+
# Unknown values just use the default (existing behavior)
42+
logger.warning(
43+
"[regex_chans] Unknown status: %s, falling back to default",
44+
tuple(row),
45+
)
46+
continue
47+
48+
new_cache[(conn, chan)] = value
3449

3550
status_cache.clear()
3651
status_cache.update(new_cache)
3752

3853

39-
def set_status(db, conn, chan, status):
54+
def set_status(db, conn, chan, status: bool):
55+
status_value = ENABLED if status else DISABLED
4056
if (conn, chan) in status_cache:
4157
# if we have a set value, update
4258
db.execute(
4359
table.update()
44-
.values(status=status)
60+
.values(status=status_value)
4561
.where(table.c.connection == conn)
4662
.where(table.c.channel == chan)
4763
)
4864
else:
4965
# otherwise, insert
5066
db.execute(
51-
table.insert().values(connection=conn, channel=chan, status=status)
67+
table.insert().values(
68+
connection=conn, channel=chan, status=status_value
69+
)
5270
)
71+
5372
db.commit()
73+
load_cache(db)
5474

5575

5676
def delete_status(db, conn, chan):
@@ -59,7 +79,9 @@ def delete_status(db, conn, chan):
5979
.where(table.c.connection == conn)
6080
.where(table.c.channel == chan)
6181
)
82+
6283
db.commit()
84+
load_cache(db)
6385

6486

6587
@hook.sieve()
@@ -69,17 +91,18 @@ def sieve_regex(bot, event, _hook):
6991
and event.chan.startswith("#")
7092
and _hook.plugin.title != "factoids"
7193
):
72-
status = status_cache.get((event.conn.name, event.chan))
73-
if status != "ENABLED" and (
74-
status == "DISABLED" or not default_enabled
75-
):
94+
status = status_cache.get(
95+
(event.conn.name, event.chan), default_enabled
96+
)
97+
if not status:
7698
logger.info(
7799
"[%s] Denying %s from %s",
78100
event.conn.name,
79101
_hook.function_name,
80102
event.chan,
81103
)
82104
return None
105+
83106
logger.info(
84107
"[%s] Allowing %s to %s",
85108
event.conn.name,
@@ -90,27 +113,30 @@ def sieve_regex(bot, event, _hook):
90113
return event
91114

92115

93-
def change_status(db, event, status):
94-
text = event.text.strip().lower()
116+
def parse_args(text: str, chan: str) -> str:
117+
text = text.strip().lower()
95118
if not text:
96-
channel = event.chan
119+
channel = chan
97120
elif text.startswith("#"):
98121
channel = text
99122
else:
100123
channel = f"#{text}"
101124

125+
return channel
126+
127+
128+
def change_status(db, event, status):
129+
channel = parse_args(event.text, event.chan)
102130
action = "Enabling" if status else "Disabling"
103131
event.message(
104132
"{} regex matching (youtube, etc) (issued by {})".format(
105133
action, event.nick
106134
),
107135
target=channel,
108136
)
137+
109138
event.notice(f"{action} regex matching (youtube, etc) in channel {channel}")
110-
set_status(
111-
db, event.conn.name, channel, "ENABLED" if status else "DISABLED"
112-
)
113-
load_cache(db)
139+
set_status(db, event.conn.name, channel, status)
114140

115141

116142
@hook.command(autohelp=False, permissions=["botcontrol"])
@@ -128,46 +154,29 @@ def disableregex(db, event):
128154
@hook.command(autohelp=False, permissions=["botcontrol"])
129155
def resetregex(text, db, conn, chan, nick, message, notice):
130156
"""[chan] - Reset regex hook status in [chan] (default: current channel)"""
131-
text = text.strip().lower()
132-
if not text:
133-
channel = chan
134-
elif text.startswith("#"):
135-
channel = text
136-
else:
137-
channel = f"#{text}"
138-
157+
channel = parse_args(text, chan)
139158
message(
140159
"Resetting regex matching setting (youtube, etc) (issued by {})".format(
141160
nick
142161
),
143162
target=channel,
144163
)
164+
145165
notice(
146166
"Resetting regex matching setting (youtube, etc) in channel {}".format(
147167
channel
148168
)
149169
)
170+
150171
delete_status(db, conn.name, channel)
151-
load_cache(db)
152172

153173

154174
@hook.command(autohelp=False, permissions=["botcontrol"])
155175
def regexstatus(text, conn, chan):
156176
"""[chan] - Get status of regex hooks in [chan] (default: current channel)"""
157-
text = text.strip().lower()
158-
if not text:
159-
channel = chan
160-
elif text.startswith("#"):
161-
channel = text
162-
else:
163-
channel = f"#{text}"
164-
status = status_cache.get((conn.name, chan))
165-
if status is None:
166-
if default_enabled:
167-
status = "ENABLED"
168-
else:
169-
status = "DISABLED"
170-
return f"Regex status for {channel}: {status}"
177+
channel = parse_args(text, chan)
178+
status = status_cache.get((conn.name, chan), default_enabled)
179+
return f"Regex status for {channel}: {ENABLED if status else DISABLED}"
171180

172181

173182
@hook.command(autohelp=False, permissions=["botcontrol"])
@@ -177,5 +186,7 @@ def listregex(conn):
177186
for (conn_name, chan), status in status_cache.items():
178187
if conn_name != conn.name:
179188
continue
180-
values.append(f"{chan}: {status}")
189+
190+
values.append(f"{chan}: {ENABLED if status else DISABLED}")
191+
181192
return ", ".join(values)
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
from plugins.core import regex_chans
2+
from tests.util.mock_conn import MockConn
3+
from tests.util.mock_db import MockDB
4+
5+
6+
def test_status_new(mock_db: MockDB):
7+
regex_chans.table.create(mock_db.engine)
8+
with mock_db.session() as session:
9+
mock_db.load_data(regex_chans.table, [])
10+
11+
regex_chans.load_cache(session)
12+
13+
regex_chans.set_status(session, "net", "#chan", True)
14+
15+
assert mock_db.get_data(regex_chans.table) == [
16+
("net", "#chan", "ENABLED")
17+
]
18+
19+
assert regex_chans.status_cache == {("net", "#chan"): True}
20+
21+
22+
def test_status_existing(mock_db: MockDB):
23+
regex_chans.table.create(mock_db.engine)
24+
with mock_db.session() as session:
25+
mock_db.load_data(
26+
regex_chans.table,
27+
[{"connection": "net", "channel": "#chan", "status": "DISABLED"}],
28+
)
29+
30+
regex_chans.load_cache(session)
31+
32+
regex_chans.set_status(session, "net", "#chan", True)
33+
34+
assert mock_db.get_data(regex_chans.table) == [
35+
("net", "#chan", "ENABLED")
36+
]
37+
38+
assert regex_chans.status_cache == {("net", "#chan"): True}
39+
40+
41+
def test_delete_status(mock_db: MockDB):
42+
regex_chans.table.create(mock_db.engine)
43+
with mock_db.session() as session:
44+
mock_db.load_data(
45+
regex_chans.table,
46+
[{"connection": "net", "channel": "#chan", "status": "DISABLED"}],
47+
)
48+
49+
regex_chans.load_cache(session)
50+
51+
regex_chans.delete_status(session, "net", "#chan")
52+
53+
assert mock_db.get_data(regex_chans.table) == []
54+
55+
assert regex_chans.status_cache == {}
56+
57+
58+
def test_listregex(mock_db: MockDB):
59+
regex_chans.table.create(mock_db.engine)
60+
with mock_db.session() as session:
61+
mock_db.load_data(
62+
regex_chans.table,
63+
[
64+
{"connection": "net", "channel": "#chan", "status": "DISABLED"},
65+
{"connection": "net", "channel": "#chan1", "status": "ENABLED"},
66+
{
67+
"connection": "net",
68+
"channel": "#chan2",
69+
"status": "DISABLED",
70+
},
71+
{
72+
"connection": "net",
73+
"channel": "#chan3",
74+
"status": "DISABLED",
75+
},
76+
{
77+
"connection": "net1",
78+
"channel": "#chan3",
79+
"status": "DISABLED",
80+
},
81+
],
82+
)
83+
84+
regex_chans.load_cache(session)
85+
86+
conn = MockConn(name="net")
87+
assert (
88+
regex_chans.listregex(conn)
89+
== "#chan: DISABLED, #chan1: ENABLED, #chan2: DISABLED, #chan3: DISABLED"
90+
)

0 commit comments

Comments
 (0)