registration implemented
This commit is contained in:
18
SprintLib/BaseDaemon.py
Normal file
18
SprintLib/BaseDaemon.py
Normal file
@@ -0,0 +1,18 @@
|
||||
import asyncio
|
||||
import sys
|
||||
from time import sleep
|
||||
|
||||
|
||||
class BaseDaemon:
|
||||
def command(self):
|
||||
raise NotImplementedError()
|
||||
|
||||
async def execute(self):
|
||||
cmd = self.command()
|
||||
proc = await asyncio.create_subprocess_shell(cmd, stdin=sys.stdin, stdout=sys.stdout, stderr=sys.stderr)
|
||||
stdout, stderr = await proc.communicate()
|
||||
print(f"[{cmd!r} exited with {proc.returncode}]")
|
||||
if stdout:
|
||||
print(f"[stdout]\n{stdout.decode()}")
|
||||
if stderr:
|
||||
print(f"[stderr]\n{stderr.decode()}")
|
72
SprintLib/BaseView.py
Normal file
72
SprintLib/BaseView.py
Normal file
@@ -0,0 +1,72 @@
|
||||
from django.core.handlers.wsgi import WSGIRequest
|
||||
from django.http import HttpResponseRedirect
|
||||
from django.shortcuts import render
|
||||
from django.utils import timezone
|
||||
|
||||
from SprintLib.EntityStorage import EntityStorage
|
||||
from Main.models import *
|
||||
|
||||
|
||||
class AccessError(Exception):
|
||||
pass
|
||||
|
||||
|
||||
class BaseView:
|
||||
request: WSGIRequest = None
|
||||
context: dict = {}
|
||||
entities = EntityStorage()
|
||||
required_login: bool = None
|
||||
view_file: str = None
|
||||
|
||||
@classmethod
|
||||
def as_view(cls):
|
||||
def execute(request):
|
||||
if request.user.is_authenticated:
|
||||
user_info = request.user.userinfo
|
||||
user_info.last_request = timezone.now()
|
||||
user_info.save()
|
||||
c = cls()
|
||||
if c.required_login is not None:
|
||||
if c.required_login and not request.user.is_authenticated:
|
||||
return HttpResponseRedirect("/enter")
|
||||
if not c.required_login and request.user.is_authenticated:
|
||||
return HttpResponseRedirect("/")
|
||||
request_method = request.method.lower()
|
||||
c.request = request
|
||||
for key in request.GET.keys():
|
||||
if key.endswith("_id"):
|
||||
model_name = key.rstrip("_id")
|
||||
c.entities.add(
|
||||
model_name,
|
||||
eval(model_name.capitalize()).objects.get(
|
||||
id=int(request.GET[key])
|
||||
),
|
||||
)
|
||||
context = c.entities.entities
|
||||
if "action" in request.POST.keys():
|
||||
request_method += "_" + request.POST["action"]
|
||||
method = getattr(c, request_method, None)
|
||||
try:
|
||||
data = c.pre_handle()
|
||||
if method:
|
||||
if data is None:
|
||||
data = method()
|
||||
if type(data) == str:
|
||||
return HttpResponseRedirect(data)
|
||||
if data is not None:
|
||||
return data
|
||||
context = {**context, **c.context}
|
||||
return render(request, c.view_file, context)
|
||||
except AccessError:
|
||||
return HttpResponseRedirect("/")
|
||||
|
||||
return execute
|
||||
|
||||
def pre_handle(self):
|
||||
pass
|
||||
|
||||
def get(self):
|
||||
pass
|
||||
|
||||
def post(self):
|
||||
pass
|
6
SprintLib/EntityStorage.py
Normal file
6
SprintLib/EntityStorage.py
Normal file
@@ -0,0 +1,6 @@
|
||||
class EntityStorage:
|
||||
entities = {}
|
||||
|
||||
def add(self, name, entity):
|
||||
self.entities[name] = entity
|
||||
setattr(self, name, entity)
|
0
SprintLib/__init__.py
Normal file
0
SprintLib/__init__.py
Normal file
80
SprintLib/testers/BaseTester.py
Normal file
80
SprintLib/testers/BaseTester.py
Normal file
@@ -0,0 +1,80 @@
|
||||
from os import listdir
|
||||
from os.path import join
|
||||
from shutil import copyfile, rmtree
|
||||
from subprocess import call, TimeoutExpired
|
||||
|
||||
from Main.models import ExtraFile
|
||||
from Sprint.settings import CONSTS
|
||||
from SprintLib.utils import copy_content
|
||||
|
||||
|
||||
class TestException(Exception):
|
||||
pass
|
||||
|
||||
|
||||
class BaseTester:
|
||||
working_directory = "app"
|
||||
|
||||
def before_test(self):
|
||||
files = [file for file in listdir(self.solution.testing_directory) if file.endswith('.' + self.solution.language.file_type)]
|
||||
code = self.solution.exec_command(f'{self.build_command} {" ".join(files)}', working_directory=self.working_directory)
|
||||
if code != 0:
|
||||
raise TestException('CE')
|
||||
|
||||
def test(self, filename):
|
||||
code = self.solution.exec_command(
|
||||
f"< {filename} {self.command} > output.txt",
|
||||
timeout=self.solution.task.time_limit / 1000,
|
||||
)
|
||||
if code != 0:
|
||||
raise TestException("RE")
|
||||
result = open(
|
||||
join(self.solution.testing_directory, "output.txt"), "r"
|
||||
).read()
|
||||
if result.strip() != self.predicted.strip():
|
||||
raise TestException("WA")
|
||||
|
||||
def after_test(self):
|
||||
pass
|
||||
|
||||
@property
|
||||
def command(self):
|
||||
return "./executable.exe"
|
||||
|
||||
@property
|
||||
def build_command(self):
|
||||
return ""
|
||||
|
||||
def __init__(self, solution):
|
||||
self.solution = solution
|
||||
|
||||
def execute(self):
|
||||
copy_content(self.solution.directory, self.solution.testing_directory, ('test_dir',))
|
||||
self.solution.result = CONSTS["testing_status"]
|
||||
self.solution.save()
|
||||
call(
|
||||
f"docker run --name solution_{self.solution.id} --volume={self.solution.testing_directory}:/{self.working_directory} -t -d {self.solution.language.image}",
|
||||
shell=True,
|
||||
)
|
||||
for file in ExtraFile.objects.filter(task=self.solution.task):
|
||||
copyfile(file.path, join(self.solution.testing_directory, file.filename))
|
||||
try:
|
||||
self.before_test()
|
||||
for test in self.solution.task.tests:
|
||||
if not test.filename.endswith(".a"):
|
||||
self.predicted = ExtraFile.objects.get(
|
||||
task=self.solution.task, filename=test.filename + ".a"
|
||||
).text
|
||||
self.test(test.filename)
|
||||
self.after_test()
|
||||
self.solution.result = CONSTS["ok_status"]
|
||||
except TestException as e:
|
||||
self.solution.result = str(e)
|
||||
except TimeoutExpired:
|
||||
self.solution.result = "TL"
|
||||
except Exception as e:
|
||||
self.solution.result = "TE"
|
||||
print(str(e))
|
||||
self.solution.save()
|
||||
call(f"docker rm --force solution_{self.solution.id}", shell=True)
|
||||
rmtree(self.solution.testing_directory)
|
11
SprintLib/testers/CSharpTester.py
Normal file
11
SprintLib/testers/CSharpTester.py
Normal file
@@ -0,0 +1,11 @@
|
||||
from SprintLib.testers import BaseTester
|
||||
|
||||
|
||||
class CSharpTester(BaseTester):
|
||||
@property
|
||||
def build_command(self):
|
||||
return "csc /out:executable.exe"
|
||||
|
||||
@property
|
||||
def command(self):
|
||||
return "mono executable.exe"
|
9
SprintLib/testers/CppTester.py
Normal file
9
SprintLib/testers/CppTester.py
Normal file
@@ -0,0 +1,9 @@
|
||||
from os import listdir
|
||||
|
||||
from SprintLib.testers import BaseTester, TestException
|
||||
|
||||
|
||||
class CppTester(BaseTester):
|
||||
@property
|
||||
def build_command(self):
|
||||
return "g++ -o executable.exe"
|
8
SprintLib/testers/GoTester.py
Normal file
8
SprintLib/testers/GoTester.py
Normal file
@@ -0,0 +1,8 @@
|
||||
from SprintLib.testers import BaseTester
|
||||
|
||||
|
||||
class GoTester(BaseTester):
|
||||
working_directory = "../app"
|
||||
|
||||
def build_command(self):
|
||||
return "go build -o executable.exe"
|
23
SprintLib/testers/JavaTester.py
Normal file
23
SprintLib/testers/JavaTester.py
Normal file
@@ -0,0 +1,23 @@
|
||||
from os import listdir
|
||||
|
||||
from SprintLib.testers import BaseTester, TestException
|
||||
|
||||
|
||||
class JavaTester(BaseTester):
|
||||
_executable = None
|
||||
|
||||
def before_test(self):
|
||||
files = [file for file in listdir(self.solution.testing_directory) if file.endswith('.java')]
|
||||
code = self.solution.exec_command(f"javac {' '.join(files)}")
|
||||
if code != 0:
|
||||
raise TestException('CE')
|
||||
for file in listdir(self.solution.testing_directory):
|
||||
if file.endswith('.class'):
|
||||
self._executable = file.rstrip('.class')
|
||||
break
|
||||
if self._executable is None:
|
||||
raise TestException("TE")
|
||||
|
||||
@property
|
||||
def command(self):
|
||||
return f"java -classpath . {self._executable}"
|
15
SprintLib/testers/KotlinTester.py
Normal file
15
SprintLib/testers/KotlinTester.py
Normal file
@@ -0,0 +1,15 @@
|
||||
from os import listdir
|
||||
|
||||
from SprintLib.testers import BaseTester, TestException
|
||||
|
||||
|
||||
class KotlinTester(BaseTester):
|
||||
def before_test(self):
|
||||
files = [file for file in listdir(self.solution.testing_directory) if file.endswith('.kt')]
|
||||
code = self.solution.exec_command(f'kotlinc {" ".join(files)} -include-runtime -d solution.jar')
|
||||
if code != 0:
|
||||
raise TestException('CE')
|
||||
|
||||
@property
|
||||
def command(self):
|
||||
return "java -jar solution.jar"
|
19
SprintLib/testers/Python3Tester.py
Normal file
19
SprintLib/testers/Python3Tester.py
Normal file
@@ -0,0 +1,19 @@
|
||||
from os import listdir
|
||||
|
||||
from SprintLib.testers.BaseTester import BaseTester, TestException
|
||||
|
||||
|
||||
class Python3Tester(BaseTester):
|
||||
file = None
|
||||
|
||||
def before_test(self):
|
||||
for file in listdir(self.solution.testing_directory):
|
||||
if file.endswith(".py"):
|
||||
self.file = file
|
||||
break
|
||||
if self.file is None:
|
||||
raise TestException("TE")
|
||||
|
||||
@property
|
||||
def command(self):
|
||||
return f"python {self.file}"
|
7
SprintLib/testers/__init__.py
Normal file
7
SprintLib/testers/__init__.py
Normal file
@@ -0,0 +1,7 @@
|
||||
from .BaseTester import *
|
||||
from .Python3Tester import *
|
||||
from .CppTester import *
|
||||
from .GoTester import *
|
||||
from .JavaTester import *
|
||||
from .CSharpTester import *
|
||||
from .KotlinTester import *
|
15
SprintLib/utils.py
Normal file
15
SprintLib/utils.py
Normal file
@@ -0,0 +1,15 @@
|
||||
from os import listdir
|
||||
from os.path import isfile, join
|
||||
from shutil import copyfile, copytree
|
||||
|
||||
|
||||
def copy_content(from_dir, to_dir, exc=()):
|
||||
for file in listdir(from_dir):
|
||||
if file in exc:
|
||||
continue
|
||||
full_path = join(from_dir, file)
|
||||
if isfile(full_path):
|
||||
func = copyfile
|
||||
else:
|
||||
func = copytree
|
||||
func(full_path, join(to_dir, file))
|
Reference in New Issue
Block a user