diff --git a/Main/models/mixins.py b/Main/models/mixins.py index 21c14a9..d877b26 100644 --- a/Main/models/mixins.py +++ b/Main/models/mixins.py @@ -11,7 +11,10 @@ class FileStorageMixin: @cached_property def text(self): - return self.bytes.decode("utf-8") + try: + return self.bytes.decode("utf-8") + except UnicodeDecodeError: + return "" def write(self, bytes): self.fs_id = write_bytes(bytes) diff --git a/Main/models/solution.py b/Main/models/solution.py index f71823d..0847b9d 100644 --- a/Main/models/solution.py +++ b/Main/models/solution.py @@ -4,6 +4,7 @@ from shutil import rmtree from subprocess import call from django.contrib.auth.models import User +from django.db.models import JSONField from django.db import models from django.utils import timezone @@ -22,6 +23,7 @@ class Solution(models.Model): result = models.TextField(default=CONSTS["in_queue_status"]) test = models.IntegerField(default=None, null=True) set = models.ForeignKey(Set, null=True, on_delete=models.SET_NULL) + extras = JSONField(default=dict) class Meta: indexes = [ diff --git a/SprintLib/testers/BaseTester.py b/SprintLib/testers/BaseTester.py index 558b6c5..44e3ec1 100644 --- a/SprintLib/testers/BaseTester.py +++ b/SprintLib/testers/BaseTester.py @@ -6,7 +6,7 @@ from Main.management.commands.bot import bot from Main.models import ExtraFile, SolutionFile from Main.models.progress import Progress from Sprint.settings import CONSTS -from SprintLib.utils import get_bytes +from SprintLib.utils import get_bytes, Timer class TestException(Exception): @@ -121,7 +121,16 @@ class BaseTester: print('predicted:', self.predicted) self.solution.test = int(test.filename) self.solution.save() - self.test(test.filename) + try: + with Timer(self.solution, test.filename) as timer: + self.test(test.filename) + finally: + self.solution.extras[test.filename]['predicted'] = test.text + if exists(join(self.path, "output.txt")): + try: + self.solution.extras[test.filename]['output'] = open(join(self.path, 'output.txt'), 'r').read() + except UnicodeDecodeError: + self.solution.extras[test.filename]['output'] = '' self.after_test() self.solution.result = CONSTS["ok_status"] self.solution.test = None diff --git a/SprintLib/utils.py b/SprintLib/utils.py index fda8778..0ca8c5b 100644 --- a/SprintLib/utils.py +++ b/SprintLib/utils.py @@ -1,3 +1,4 @@ +import datetime from random import choice from requests import get, post @@ -26,3 +27,20 @@ def delete_file(num: int): def generate_token(): letters = '1234567890qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM' return ''.join([choice(letters) for _ in range(30)]) + + +class Timer: + start_time = None + end_time = None + + def __init__(self, solution, test): + self.solution = solution + self.test = test + + def __enter__(self): + assert self.start_time is None + self.start_time = datetime.datetime.now() + + def __exit__(self, exc_type, exc_val, exc_tb): + self.end_time = datetime.datetime.now() + self.solution.extras[self.test]['time_spent'] = (self.end_time - self.start_time).total_seconds() * 1000