dev #10

Merged
李衍志523370910113 merged 238 commits from dev into master 2025-03-05 16:20:39 +08:00
6 changed files with 48 additions and 100 deletions
Showing only changes of commit 16c7cb517a - Show all commits

View File

@ -10,37 +10,6 @@ from joj3_config_generator.lib.task import (
get_executorWithConfig,
)
from joj3_config_generator.models import joj1, repo, result, task
from joj3_config_generator.lib.task import (
fix_diff,
fix_dummy,
fix_keyword,
fix_result_detail,
get_conf_stage,
get_executorWithConfig,
)
from joj3_config_generator.models import joj1, repo, result, task
from joj3_config_generator.lib.repo import getHealthcheckConfig, getTeapotConfig
from joj3_config_generator.lib.task import (
fix_comment,
fix_diff,
fix_keyword,
fix_result_detail,
get_conf_stage,
get_executorWithConfig,
)
from joj3_config_generator.models import (
Cmd,
CmdFile,
ExecutorConfig,
ExecutorWithConfig,
ParserConfig,
Repo,
ResultConfig,
Stage,
StageConfig,
Task,
TeapotConfig,
)
# FIXME: LLM generated convert function, only for demostration
@ -58,8 +27,6 @@ def convert(repo_conf: repo.Config, task_conf: task.Config) -> result.Config:
else -1
),
stage=result.Stage(stages=[], sandbox_token=repo_conf.sandbox_token),
teapot=result.Teapot(),
stage=StageConfig(stages=[], sandbox_token=repo_conf.sandbox_token),
teapot=getTeapotConfig(repo_conf, task_conf),
)
jon-lee marked this conversation as resolved Outdated

Make this Path.home() default to /home/tt. For now, create a const for this dir.

Make this `Path.home()` default to `/home/tt`. For now, create a const for this dir.

fixed

fixed

View File

@ -1,11 +0,0 @@
from joj3_config_generator.models.repo import Repo as Repo
from joj3_config_generator.models.result import Cmd as Cmd
from joj3_config_generator.models.result import CmdFile as CmdFile
from joj3_config_generator.models.result import ExecutorConfig as ExecutorConfig
from joj3_config_generator.models.result import ExecutorWithConfig as ExecutorWithConfig
from joj3_config_generator.models.result import ParserConfig as ParserConfig
from joj3_config_generator.models.result import ResultConfig as ResultConfig
from joj3_config_generator.models.result import Stage as Stage
from joj3_config_generator.models.result import StageConfig as StageConfig
from joj3_config_generator.models.result import TeapotConfig as TeapotConfig
from joj3_config_generator.models.task import Task as Task

View File

@ -2,19 +2,7 @@ import hashlib
import socket
import tempfile
from joj3_config_generator.models import (
Cmd,
CmdFile,
ExecutorConfig,
ExecutorWithConfig,
ParserConfig,
Repo,
ResultConfig,
Stage,
StageConfig,
Task,
TeapotConfig,
)
from joj3_config_generator.models import joj1, repo, result, task
def get_temp_directory() -> str:
@ -26,8 +14,8 @@ def getGradingRepoName() -> str:
return f"{host_name.split('-')[0]}-joj"
def getTeapotConfig(repo_conf: Repo, task_conf: Task) -> TeapotConfig:
teapot = TeapotConfig(
def getTeapotConfig(repo_conf: repo.Config, task_conf: task.Config) -> result.Teapot:
teapot = result.Teapot(
# TODO: fix the log path
log_path=f"{task_conf.task.replace(' ', '-')}-joint-teapot-debug.log",
scoreboard_path=f"{task_conf.task.replace(' ', '-')}-scoreboard.csv",
@ -37,7 +25,7 @@ def getTeapotConfig(repo_conf: Repo, task_conf: Task) -> TeapotConfig:
return teapot
def getHealthcheckCmd(repo_conf: Repo) -> Cmd:
def getHealthcheckCmd(repo_conf: repo.Config) -> result.Cmd:
repoSize = repo_conf.max_size
immutable = repo_conf.files.immutable
repo_size = f"-repoSize={str(repoSize)} "
@ -64,11 +52,11 @@ def getHealthcheckCmd(repo_conf: Repo) -> Cmd:
args = args + immutable_files
cmd = Cmd(
cmd = result.Cmd(
args=args.split(),
# FIXME: easier to edit within global scope
copy_in={
f"/{get_temp_directory()}/repo-health-checker": CmdFile(
f"/{get_temp_directory()}/repo-health-checker": result.CmdFile(
src=f"/{get_temp_directory()}/repo-health-checker"
)
},
@ -76,15 +64,17 @@ def getHealthcheckCmd(repo_conf: Repo) -> Cmd:
return cmd
def getHealthcheckConfig(repo_conf: Repo, task_conf: Task) -> Stage:
healthcheck_stage = Stage(
def getHealthcheckConfig(
repo_conf: repo.Config, task_conf: task.Config
) -> result.StageDetail:
healthcheck_stage = result.StageDetail(
name="healthcheck",
group="",
executor=ExecutorConfig(
executor=result.Executor(
name="sandbox",
with_=ExecutorWithConfig(default=getHealthcheckCmd(repo_conf), cases=[]),
with_=result.ExecutorWith(default=getHealthcheckCmd(repo_conf), cases=[]),
),
parsers=[ParserConfig(name="healthcheck", with_={"score": 0, "comment": ""})],
parsers=[result.Parser(name="healthcheck", with_={"score": 0, "comment": ""})],
)
return healthcheck_stage

View File

@ -2,20 +2,13 @@ from typing import Tuple
import rtoml
from joj3_config_generator.models import (
ExecutorConfig,
ExecutorWithConfig,
ParserConfig,
)
from joj3_config_generator.models.result import Cmd, CmdFile, OptionalCmd
from joj3_config_generator.models.result import Stage as ResultStage
from joj3_config_generator.models.task import Stage as TaskStage
from joj3_config_generator.models import joj1, repo, result, task
def get_conf_stage(
task_stage: TaskStage, executor_with_config: ExecutorWithConfig
) -> ResultStage:
conf_stage = ResultStage(
task_stage: task.Stage, executor_with_config: result.ExecutorWith
) -> result.StageDetail:
conf_stage = result.StageDetail(
name=task_stage.name if task_stage.name is not None else "",
# TODO: we may have cq in future
group=(
@ -23,12 +16,12 @@ def get_conf_stage(
if (task_stage.name is not None) and ("judge" in task_stage.name)
else None
),
executor=ExecutorConfig(
executor=result.Executor(
name="sandbox",
with_=executor_with_config,
),
parsers=(
[ParserConfig(name=parser, with_={}) for parser in task_stage.parsers]
[result.Parser(name=parser, with_={}) for parser in task_stage.parsers]
if task_stage.parsers is not None
else []
),
@ -37,8 +30,8 @@ def get_conf_stage(
def get_executorWithConfig(
task_stage: TaskStage, cached: list[str]
) -> Tuple[ExecutorWithConfig, list[str]]:
task_stage: task.Stage, cached: list[str]
) -> Tuple[result.ExecutorWith, list[str]]:
file_import = (
task_stage.files.import_
if hasattr(task_stage, "files")
@ -55,11 +48,11 @@ def get_executorWithConfig(
and (task_stage.files is not None)
else []
)
executor_with_config = ExecutorWithConfig(
default=Cmd(
executor_with_config = result.ExecutorWith(
default=result.Cmd(
args=(task_stage.command.split() if task_stage.command is not None else []),
copy_in={
file: CmdFile(src=f"/home/tt/.config/joj/{file}")
file: result.CmdFile(src=f"/home/tt/.config/joj/{file}")
for file in copy_in_files
},
copy_in_cached={file: file for file in copy_in_files},
@ -79,7 +72,7 @@ def get_executorWithConfig(
if task_stage.limit is not None and task_stage.limit.mem is not None
else 4 * 1_024 * 1_024
),
stderr=CmdFile(
stderr=result.CmdFile(
name="stderr",
max=(
task_stage.limit.stderr * 1_000_000_000
@ -88,7 +81,7 @@ def get_executorWithConfig(
else 4 * 1_024 * 1_024
),
),
stdout=CmdFile(
stdout=result.CmdFile(
name="stdout",
max=(
task_stage.limit.stdout * 1_000_000_000
@ -107,7 +100,9 @@ def get_executorWithConfig(
return (executor_with_config, cached)
def fix_keyword(task_stage: TaskStage, conf_stage: ResultStage) -> ResultStage:
def fix_keyword(
task_stage: task.Stage, conf_stage: result.StageDetail
) -> result.StageDetail:
keyword_parser = ["clangtidy", "keyword", "cppcheck"] # TODO: may add cpplint
if task_stage.parsers is not None:
for parser in task_stage.parsers:
@ -128,7 +123,9 @@ def fix_keyword(task_stage: TaskStage, conf_stage: ResultStage) -> ResultStage:
return conf_stage
def fix_result_detail(task_stage: TaskStage, conf_stage: ResultStage) -> ResultStage:
def fix_result_detail(
task_stage: task.Stage, conf_stage: result.StageDetail
) -> result.StageDetail:
if (task_stage.parsers is not None) and ("result-detail" in task_stage.parsers):
result_detail_parser = next(
p for p in conf_stage.parsers if p.name == "result-detail"
@ -159,7 +156,9 @@ def fix_result_detail(task_stage: TaskStage, conf_stage: ResultStage) -> ResultS
return conf_stage
def fix_comment(task_stage: TaskStage, conf_stage: ResultStage) -> ResultStage:
def fix_comment(
task_stage: task.Stage, conf_stage: result.StageDetail
) -> result.StageDetail:
comment_parser = [
"dummy",
"result-status",
@ -180,7 +179,9 @@ def fix_comment(task_stage: TaskStage, conf_stage: ResultStage) -> ResultStage:
return conf_stage
def fix_diff(task_stage: TaskStage, conf_stage: ResultStage) -> ResultStage:
def fix_diff(
task_stage: task.Stage, conf_stage: result.StageDetail
) -> result.StageDetail:
if task_stage.parsers is not None and "diff" in task_stage.parsers:
diff_parser = next((p for p in conf_stage.parsers if p.name == "diff"), None)
skip = task_stage.skip or []
@ -213,8 +214,8 @@ def fix_diff(task_stage: TaskStage, conf_stage: ResultStage) -> ResultStage:
)
stage_cases.append(
OptionalCmd(
stdin=CmdFile(
result.OptionalCmd(
stdin=result.CmdFile(
src=f"/home/tt/.config/joj/{conf_stage.name}/{case}.in"
),
cpu_limit=cpu_limit,

View File

@ -1,5 +1,5 @@
from datetime import datetime
jon-lee marked this conversation as resolved Outdated

every field in this file should not be optional. we give an default value here if any field does not exist

every field in this file should not be optional. we give an default value here if any field does not exist

and use underscore naming in this file

and use underscore naming in this file

every field in this file should not be optional. we give an default value here if any field does not exist

fixed

> every field in this file should not be optional. we give an default value here if any field does not exist fixed

and use underscore naming in this file

fixed.

> and use underscore naming in this file fixed.
from typing import Any, Dict, Optional, Type, List
from typing import Any, Dict, List, Optional, Type
from pydantic import BaseModel, Field, root_validator
from pydantic import BaseModel, Field, root_validator
@ -34,9 +34,10 @@ class ParserDiff(BaseModel):
class Files(BaseModel):
import_: Optional[List[str]] = Field(serialization_alias="import", validation_alias="import")
export: Optional[List[str]]
import_: Optional[List[str]] = Field(
[], serialization_alias="import", validation_alias="import"
)
export: Optional[List[str]] = []
class Limit(BaseModel):

View File

@ -18,7 +18,7 @@
"/<function",
"get_temp_directory",
"at",
"0x7f64f5d532e0>/repo-health-checker",
"0x7f19f8920180>/repo-health-checker",
"-root=.",
"-repoSize=50.5",
"-meta=main.py",
@ -70,8 +70,8 @@
"cpuRateLimit": 0,
"cpuSetLimit": "",
"copyIn": {
"//tmp/repo-checker-lf3ranpy/repo-health-checker": {
"src": "//tmp/repo-checker-gd58j2qv/repo-health-checker",
"//tmp/repo-checker-5txkd_qm/repo-health-checker": {
"src": "//tmp/repo-checker-i9n16_cy/repo-health-checker",
"content": null,
"fileId": null,
"name": null,