Skip to content

Commit f56b427

Browse files
committed
Add a util to create the session and freeze the choices
1 parent d765313 commit f56b427

File tree

2 files changed

+87
-3
lines changed

2 files changed

+87
-3
lines changed

code_submitter/utils.py

Lines changed: 45 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
1-
from typing import Dict, Tuple
1+
from typing import cast, Dict, Tuple
22
from zipfile import ZipFile
33

44
import databases
55
from sqlalchemy.sql import select
66

7-
from .tables import Archive, ChoiceHistory
7+
from .tables import Archive, Session, ChoiceHistory, ChoiceForSession
88

99

1010
async def get_chosen_submissions(
@@ -35,6 +35,49 @@ async def get_chosen_submissions(
3535
return {x['team']: (x['id'], x['content']) for x in rows}
3636

3737

38+
async def create_session(
39+
database: databases.Database,
40+
name: str,
41+
*,
42+
by_username: str,
43+
) -> int:
44+
"""
45+
Return a mapping of teams to their the chosen archive.
46+
"""
47+
48+
# Note: Ideally we'd group by team in SQL, however that doesn't seem to work
49+
# properly -- we don't get the ordering applied before the grouping.
50+
51+
async with database.transaction():
52+
rows = await database.fetch_all(
53+
select([
54+
ChoiceHistory.c.id,
55+
Archive.c.team,
56+
]).select_from(
57+
Archive.join(ChoiceHistory),
58+
).order_by(
59+
Archive.c.team,
60+
ChoiceHistory.c.created.asc(),
61+
),
62+
)
63+
64+
session_id = cast(int, await database.execute(
65+
Session.insert().values(name=name, username=by_username),
66+
))
67+
68+
# Rely on later keys replacing earlier occurrences of the same key.
69+
choice_by_team = {x['team']: x['id'] for x in rows}
70+
await database.execute_many(
71+
ChoiceForSession.insert(),
72+
[
73+
{'choice_id': x, 'session_id': session_id}
74+
for x in choice_by_team.values()
75+
],
76+
)
77+
78+
return session_id
79+
80+
3881
def summarise(submissions: Dict[str, Tuple[int, bytes]]) -> str:
3982
return "".join(
4083
"{}: {}\n".format(team, id_)

tests/tests_utils.py

Lines changed: 42 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
import test_utils
66

77
from code_submitter import utils
8-
from code_submitter.tables import Archive, ChoiceHistory
8+
from code_submitter.tables import Archive, ChoiceHistory, ChoiceForSession
99

1010

1111
class UtilsTests(test_utils.InTransactionTestCase):
@@ -76,6 +76,47 @@ def test_get_chosen_submissions_multiple_chosen(self) -> None:
7676
result,
7777
)
7878

79+
def test_create_session(self) -> None:
80+
choice_id_1 = self.await_(self.database.execute(
81+
ChoiceHistory.insert().values(
82+
archive_id=8888888888,
83+
username='someone_else',
84+
created=datetime.datetime(2020, 8, 8, 12, 0),
85+
),
86+
))
87+
choice_id_2 = self.await_(self.database.execute(
88+
ChoiceHistory.insert().values(
89+
archive_id=1111111111,
90+
username='test_user',
91+
created=datetime.datetime(2020, 3, 3, 12, 0),
92+
),
93+
))
94+
self.await_(self.database.execute(
95+
ChoiceHistory.insert().values(
96+
archive_id=2222222222,
97+
username='test_user',
98+
created=datetime.datetime(2020, 2, 2, 12, 0),
99+
),
100+
))
101+
102+
session_id = self.await_(utils.create_session(
103+
self.database,
104+
"Test Session",
105+
by_username='the-user',
106+
))
107+
108+
choices = self.await_(self.database.fetch_all(
109+
ChoiceForSession.select(),
110+
))
111+
112+
self.assertEqual(
113+
[
114+
{'choice_id': choice_id_1, 'session_id': session_id},
115+
{'choice_id': choice_id_2, 'session_id': session_id},
116+
],
117+
[dict(x) for x in choices],
118+
)
119+
79120
def test_collect_submissions(self) -> None:
80121
self.await_(self.database.execute(
81122
ChoiceHistory.insert().values(

0 commit comments

Comments
 (0)