Skip to content

Commit 0e7cfdd

Browse files
committed
add get_clan_games_[start|end] utils and a few event examples
1 parent 5d27709 commit 0e7cfdd

File tree

5 files changed

+101
-27
lines changed

5 files changed

+101
-27
lines changed

coc/events.py

Lines changed: 14 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@
3535
from .players import Player
3636
from .wars import ClanWar
3737
from .errors import Maintenance, PrivateWarLog
38-
from .utils import correct_tag, get_season_end
38+
from .utils import correct_tag, get_season_end, get_clan_games_start, get_clan_games_end
3939

4040
LOG = logging.getLogger(__name__)
4141
DEFAULT_SLEEP = 10
@@ -787,21 +787,21 @@ async def _raid_poller(self):
787787
age = 0
788788
while self.loop.is_running():
789789
try:
790-
[raidlog_entry] = await self.get_raidlog("#2PP", limit=1)
791-
raidlog_entry: coc.raid.RaidLogEntry
790+
[raid_log_entry] = await self.get_raidlog("#2PP", limit=1)
791+
raid_log_entry: coc.raid.RaidLogEntry
792792
except Maintenance:
793793
await asyncio.sleep(15)
794794
except Exception:
795795
await asyncio.sleep(DEFAULT_SLEEP)
796796
else:
797-
if raidlog_entry.start_time.seconds_until + age > 0 and raidlog_entry.end_time.seconds_until > 0:
797+
if raid_log_entry.start_time.seconds_until + age > 0 and raid_log_entry.end_time.seconds_until > 0:
798798
# raid started
799799
self.dispatch("raid_weekend_start")
800-
elif raidlog_entry.end_time.seconds_until + age > 0 > raidlog_entry.end_time.seconds_until:
800+
elif raid_log_entry.end_time.seconds_until + age > 0 > raid_log_entry.end_time.seconds_until:
801801
# raid ended
802802
self.dispatch("raid_weekend_end")
803803
# sleep for response_retry + 1
804-
age = raidlog_entry._response_retry + 1
804+
age = raid_log_entry._response_retry + 1
805805
await asyncio.sleep(age)
806806
except asyncio.CancelledError:
807807
pass
@@ -825,18 +825,16 @@ async def _end_of_season_poller(self):
825825
async def _clan_games_poller(self):
826826
try:
827827
while self.loop.is_running():
828-
mute = now = datetime.utcnow()
829-
if now.day > 28 or (now.day == 28 and now.hour > 8):
830-
mute += timedelta(days=7)
831-
mute = datetime(year=mute.year, month=mute.month, day=22, hour=8, minute=0, second=0)
828+
clan_games_start = get_clan_games_start()
829+
clan_games_end = get_clan_games_end()
830+
now = datetime.utcnow()
831+
if now < clan_games_start:
832832
event = "clan_games_start"
833-
elif now.day > 22 or (now.day == 22 and now.hour > 8):
834-
mute = datetime(year=now.year, month=now.month, day=28, hour=8, minute=0, second=0)
835-
event = "clan_games_end"
833+
mute_time = clan_games_start - now
836834
else:
837-
mute = datetime(year=now.year, month=now.month, day=22, hour=8, minute=0, second=0)
838-
event = "clan_games_start"
839-
await asyncio.sleep((mute - now).total_seconds())
835+
event = "clan_games_end"
836+
mute_time = clan_games_end - now
837+
await asyncio.sleep(mute_time.total_seconds())
840838
self.dispatch(event)
841839
except asyncio.CancelledError:
842840
pass

coc/utils.py

Lines changed: 62 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -367,10 +367,68 @@ def get_season_end(month: Optional[int] = None, year: Optional[int] = None) -> d
367367
return get_season_start(month, year)
368368

369369

370+
def get_clan_games_start(time: Optional[datetime] = None) -> datetime:
371+
"""Get the datetime that the next clan games will start.
372+
373+
This goes by the assumption that clan games start at 8am UTC at the 22nd of each month.
374+
375+
.. note::
376+
377+
If you want the start of the next or running clan games, do not pass any parameters in,
378+
for any other pass a datetime in the month before.
379+
380+
Parameters
381+
----------
382+
time: Optional[datetime]
383+
Some time in the month before the clan games you want the start of.
384+
385+
Returns
386+
-------
387+
clan_games_start: :class:`datetime.datetime`
388+
The start of the next or running clan games.
389+
"""
390+
if time is None:
391+
time = datetime.utcnow()
392+
month = time.month
393+
this_months_cg_end = datetime(year=time.year, month=time.month, day=28, hour=8, minute=0, second=0)
394+
if time > this_months_cg_end:
395+
month += 1
396+
return datetime(year=time.year, month=month, day=22, hour=8, minute=0, second=0)
397+
398+
399+
def get_clan_games_end(time: Optional[datetime] = None) -> datetime:
400+
"""Get the datetime that the next clan games will end.
401+
402+
This goes by the assumption that clan games end at 8am UTC at the 28th of each month.
403+
404+
.. note::
405+
406+
If you want the end of the next or running clan games, do not pass any parameters in,
407+
for any other pass a datetime in the month before.
408+
409+
Parameters
410+
----------
411+
time: Optional[datetime]
412+
Some time in the month before the clan games you want the end of.
413+
414+
Returns
415+
-------
416+
clan_games_end: :class:`datetime.datetime`
417+
The end of the next or running clan games.
418+
"""
419+
if time is None:
420+
time = datetime.utcnow()
421+
month = time.month
422+
this_months_cg_end = datetime(year=time.year, month=time.month, day=28, hour=8, minute=0, second=0)
423+
if time > this_months_cg_end:
424+
month += 1
425+
return datetime(year=time.year, month=month, day=28, hour=8, minute=0, second=0)
426+
427+
370428
def get_raid_weekend_start(time: Optional[datetime] = None) -> datetime:
371429
"""Get the datetime that the raid weekend will start.
372430
373-
This goes by the assumption that raid weekends start at friday 7 UTC.
431+
This goes by the assumption that raid weekends start at friday 7am UTC.
374432
375433
.. note::
376434
@@ -384,10 +442,9 @@ def get_raid_weekend_start(time: Optional[datetime] = None) -> datetime:
384442
385443
Returns
386444
-------
387-
raid_weekend_end: :class:`datetime.datetime`
388-
The end of the raid weekend.
445+
raid_weekend_start: :class:`datetime.datetime`
446+
The start of the raid weekend.
389447
"""
390-
# Shift the time so that we can pretend the raid ends just after midnight
391448
if time is None:
392449
time = datetime.utcnow()
393450
time = get_raid_weekend_end(time)
@@ -398,7 +455,7 @@ def get_raid_weekend_start(time: Optional[datetime] = None) -> datetime:
398455
def get_raid_weekend_end(time: Optional[datetime] = None) -> datetime:
399456
"""Get the datetime that the raid weekend will end.
400457
401-
This goes by the assumption that raid weekends end at monday 7 UTC.
458+
This goes by the assumption that raid weekends end at monday 7am UTC.
402459
403460
.. note::
404461

docs/advanced/utils.rst

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,10 @@ Utility Functions
1717

1818
.. autofunction:: coc.utils.get_season_end
1919

20+
.. autofunction:: coc.utils.get_clan_games_start
21+
22+
.. autofunction:: coc.utils.get_clan_games_end
23+
2024
.. autofunction:: coc.utils.get_raid_weekend_start
2125

2226
.. autofunction:: coc.utils.get_raid_weekend_end

docs/miscellaneous/changelog.rst

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,11 @@ Additions:
1313
~~~~~~~~~~
1414

1515
- Added new events :func:`ClientEvents.raid_weekend_start`, :func:`ClientEvents.raid_weekend_end`,
16-
:func:`ClientEvents.clangames_start`, :func:`ClientEvents.clangames_end`,
16+
:func:`ClientEvents.clan_games_start`, :func:`ClientEvents.clan_games_end`,
1717
:func:`WarEvents.new_war` and :func:`ClanEvents.member_versus_rank`
1818

19-
- Added utility functions :func:`utils.get_raid_weekend_start`, :func:`utils.get_raid_weekend_end`
19+
- Added utility functions :func:`utils.get_clan_games_start`, :func:`utils.get_clan_games_end`
20+
:func:`utils.get_raid_weekend_start` and :func:`utils.get_raid_weekend_end`
2021

2122
- Added clan capital leaderboards
2223

examples/events_example.py

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,11 @@ async def current_war_stats(attack, war):
5656
f"attacked ({attack.defender.map_position}).{attack.defender} of {attack.defender.clan}")
5757

5858

59+
@coc.WarEvents.new_war()
60+
async def new_war(war):
61+
log.info(f"New war against {war.opponent.name} detected.")
62+
63+
5964
"""Player Events"""
6065

6166

@@ -95,13 +100,22 @@ async def on_maintenance():
95100

96101
@coc.ClientEvents.maintenance_completion()
97102
async def on_maintenance_completion(time_started):
98-
log.info("Maintenace Ended; started at %s", time_started)
103+
log.info(f"Maintenace Ended; started at {time_started}")
99104

100105

101106
@coc.ClientEvents.new_season_start()
102107
async def season_started():
103-
log.info("New season started, and will finish at %s",
104-
str(utils.get_season_end()))
108+
log.info(f"New season started, and will finish at {str(utils.get_season_end())}")
109+
110+
111+
@coc.ClientEvents.clan_games_end()
112+
async def clan_games_ended():
113+
log.info(f"Clan games have ended. The next ones will start at {str(utils.get_clan_games_start())}")
114+
115+
116+
@coc.ClientEvents.raid_weekend_start()
117+
async def raid_weekend_started():
118+
log.info(f"A new Raid Weekend started. It will last until {str(utils.get_raid_weekend_end())}")
105119

106120

107121
async def main() -> None:
@@ -150,7 +164,7 @@ def emit(self, record) -> None:
150164
sys.exit(0)
151165

152166
log.addHandler(Handler())
153-
# we don't wanna wait forever for an event, so if
167+
# we don't want to wait forever for an event, so if
154168
# it sets up OK lets call it quits.
155169
await asyncio.sleep(20)
156170
_loop = asyncio.get_event_loop()

0 commit comments

Comments
 (0)