示例#1
0
文件: parser.py 项目: ChadIImus/Kat
def parse(args: list = None):
    parser = ArgumentParser(
        description='Get, test and submit Kattis problems.',
        conflict_handler='resolve')
    parser.add_argument(
        '-n',
        '--no-override',
        action='store_true',
        help='Run the command without any of the overrides set in your config.'
    )
    sub_parsers = parser.add_subparsers(dest='command', metavar='command')

    for p in parsers:
        p(sub_parsers)

    parsed = vars(parser.parse_args(args))

    noOverride = parsed.get('no_override')
    if noOverride:
        return parsed

    cfg = getConfig()
    command = parsed.get('command')
    commandConfig = cfg.get('Default options', {}).get(command, '').strip()

    if commandConfig and args:
        configArgs = commandConfig.split()
        newArgs = unify_args(command, args, configArgs)
        return vars(parser.parse_args(newArgs))
    else:
        return parsed
示例#2
0
def get(problemName: str, data: dict):
    checkCorrectDomain(problemName, "get")
    message = ""
    folder = findProblemLocation(problemName)
    if folder is None:
        overrideLanguage = data['language']
        fetchProblem(problemName, overrideLanguage)
        message = "👍 Successfully initialized exercise " + problemName + "!"

    elif folder != "":
        unarchive(problemName)
        message = "👍 Successfully unarchived exercise " + problemName + "!"
    if message != "":
        print(message)
    else:
        print("👍 You already have " + problemName)

    if "open" in data and data['open']:
        webCommand(problemName)

    fileOpener = getConfig().get('kat', {}).get('openfilecommand')
    if fileOpener:
        file = selectProgramFile(problemName)
        subprocess.run(formatCommand(fileOpener, file).split())
    return folder
示例#3
0
文件: list.py 项目: hojelse/Kat
def collectProblems(args, options):
    session = requests.Session()
    config = getConfig()
    url = "https://open.kattis.com/problems/"
    parameters = buildParameters(args, options)
    login(config, session)
    problems = fetchProblems(url, parameters, args, session)
    return problems
示例#4
0
def getRuntime(id, problemName, session):
    user = getConfig().get("user", "username")
    url = f"{getConfigUrl('usersurl', 'users')}/{user}/submissions/{problemName}"
    response = session.get(url, headers=HEADERS)
    body = response.content.decode("utf-8")
    soup = BeautifulSoup(body, "html.parser")
    data = soup.select(
        f'table.table-kattis tbody tr[data-submission-id="{id}"] td.runtime')
    if len(data) > 0:
        return data[0].text
示例#5
0
def problem(problemName: str):
    if problemName.startswith(".\\"):
        problemName = problemName[2:]
    if problemName.endswith("\\"):
        problemName = problemName[:-1]
    if len(problemName) == 1:
        section = getConfig().get('contest')
        if problemName in section:
            return section[problemName]
    return problemName
示例#6
0
def configCommand(data):
    if 'section' not in data:
        print("Adding/updating configuration to your .kattisrc...")
        if not getConfig():
            print("""\
Something went wrong in locating the configuration file
for kattis. Have you fetched the .kattisrc? Consult the 
README.md for more details.""")
        else:
            print(
                "Successfully added default configuration to your .kattisrc!")

    elif "value" in data:
        cfg, location = getConfig(shouldReturnLocation=True)
        section = data["section"]
        option = data["option"]
        value = data["value"]
        if not cfg:
            print("""\
Something went wrong in locating the configuration file
for kattis. Have you fetched the .kattisrc? Consult the 
README.md for more details.""")
        elif cfg.has_section(section):
            if not cfg.has_option(section, option) and section.lower() in [
                    "kat", "kattis", "user"
            ]:
                print("Setting", option,
                      "was not recognized for section [" + section + "]")
            else:
                cfg.set(section, option, value)
                with open(location, "w") as configFile:
                    cfg.write(configFile)
                print("The setting", option, "from section [" + section + "]",
                      "was set to", value)
        else:
            print("Section [" + section + "]", "was not found.")

    else:
        print("""\
Invalid number of arguments, expected 
'config <section> <option> <value>'. 
Remember to put arguments with spaces in quotes.""")
示例#7
0
文件: startup.py 项目: Duckapple/Kat
def copyConfigStep():
    print("💾 Adding/updating configuration to your .kattisrc...")
    if not getConfig():
        print("""\
❌ Something went wrong in locating the configuration file
for kattis. Have you fetched the .kattisrc? Consult the 
README.md for more details.""")
        return False
    else:
        print("✅ Successfully added default configuration to your .kattisrc!")
        return True
示例#8
0
文件: config.py 项目: hojelse/Kat
def configCommand(args, options):
    if len(args) == 0:
        print("Adding/updating configuration to your .kattisrc...")
        if getConfig() == -1:
            print("""\
Something went wrong in locating the configuration file
for kattis. Have you fetched the .kattisrc? Consult the 
README.md for more details.""")
        else:
            print(
                "Successfully added default configuration to your .kattisrc!")

    elif len(args) == 3:
        cfg, location = getConfig(shouldReturnLocation=True)
        if type(cfg) is int:
            print("""\
Something went wrong in locating the configuration file
for kattis. Have you fetched the .kattisrc? Consult the 
README.md for more details.""")
        elif cfg.has_section(args[0]):
            if not cfg.has_option(args[0], args[1]) and args[0].lower() in [
                    "kat", "kattis", "user"
            ]:
                print("Setting", args[1],
                      "was not recognized for section [" + args[0] + "]")
            else:
                cfg.set(args[0], args[1], args[2])
                with open(location, "w") as configFile:
                    cfg.write(configFile)
                print("The setting", args[1], "from section [" + args[0] + "]",
                      "was set to", args[2])
        else:
            print("Section [" + args[0] + "]", "was not found.")

    else:
        print("""\
Invalid number of arguments, expected 
'config <section> <option> <value>'. 
Remember to put arguments with spaces in quotes.""")
示例#9
0
def createBoilerplate(problemName, overrideLanguage=None):
    from helpers.programSelector import guessLanguage, formatProgramFile
    cfg = getConfig()
    if overrideLanguage:
        lang = overrideLanguage.lower()
    else:
        lang = cfg.get("kat", {}).get("language").lower()
    if lang in cfg["Initialize commands"]:
        cmd = cfg["Initialize commands"].get(lang).split()
        subprocess.run([p for p in cmd], cwd=problemName)
        if lang.lower() == 'rust':
            f = open(os.path.join(problemName, 'rust-toolchain'), 'w')
            f.write('1.26.0')
            f.close()
        return
    directory = os.path.dirname(os.path.realpath(
        __file__)) + "/../boilerplate"  #todo please make this better
    boilerplates = {
        guessLanguage(formatProgramFile(f)): f
        for f in os.listdir(directory)
        if os.path.isfile(os.path.join(directory, f))
    }

    fileName = problemName
    if lang in cfg["Naming"]:
        naming = cfg.get("Naming").get(lang)
        namingFn = namingSchemeConverters[naming]
        fileName = namingFn(fileName)

    if lang.lower() in boilerplates:
        boilerplate = boilerplates[lang]
        fileType = "." + boilerplates[lang].split(".")[-1]
        shutil.copy2(
            directory + "/" + boilerplate,
            problemName + "/" + fileName + fileType,
        )
    else:
        fileType = [
            file for (file, k) in cfg["File associations"].items()
            if k.lower() == lang.lower()
        ]
        if fileType:
            open(problemName + "/" + fileName + fileType[0], "a").close()
        else:
            #Language does not exist, delete the folder

            print(
                f"Error, unable to resolve {lang} to a language that could be run. Please check if your spelling matches the one used by kat tool."
            )
            print(f"These are the supported languages:")
            print(", ".join(cfg["File associations"].values()))
示例#10
0
def contestCommand(data):
    session = requests.Session()
    contest = data.get('contest-id')
    contestData = readContest(contest, session)
    if contestData.get('timeState') == TimeState.NotStarted:
        timeTo = contestData.get('timeTo')
        print('Contest has not started yet.')
        print(f'Contest begins in {timeTo}.')
        print("Do you want to run this command again when the contest starts?")
        if not yes():
            return
        print("Waiting for contest to start...")
        while contestData.get('timeState') == TimeState.NotStarted:
            timeTo = contestData.get('timeTo')
            timeToInSeconds = timeTo.total_seconds() if timeTo is not None else -1 # the -1 denotes that we don't know how long it is to contest start, and will result in the code checking every second
            if timeToInSeconds > 10:
                time.sleep(timeToInSeconds - 10)
            else:
                time.sleep(1)
            contestData = readContest(contest, session)


    elif contestData.get('timeState') == TimeState.Ended:
        print('The contest seems to be over.')
        if len(contestData.get('problems')) > 0:
            print('Do you want to get the problems from the contest anyways?')
            if not yes():
                return
    solved = getCommand({
        **data,
        'command': 'get',
        'problem': contestData.get('problems'),
        'language': None,
    })
    #update config with new problems
    config = getConfig()
    config['contest'] = contestData['problemMap']
    saveConfig()


    if solved:
        if not data.get('submit'):
            print("Some problems were unarchived from the .solved folder:")
            print(", ".join(solved))
            print("Do you want to submit them?")
            if not yes():
                return
        for problem in solved:
            submitCommand({"problem": problem, "force": True, "archive": True})
示例#11
0
def login(session):
    config = getConfig()
    username = config.get("user", "username")
    token = config.get("user", "token")
    login_url = getConfigUrl("loginurl", "login")

    session.post(
        login_url,
        data={
            "user": username,
            "token": token,
            "script": "true"
        },
        headers=_HEADERS,
    )
示例#12
0
文件: read.py 项目: hojelse/Kat
def readCommand(arg, options):
    session = requests.Session()
    config = getConfig()
    problemName = arg
    problemUrl = "https://open.kattis.com/problems/" + problemName

    checkProblemExistence(problemName)

    if "console" not in options:
        webCommand(problemName)
    else:
        problemText = fetchProblemText(problemUrl, options, session)

        for line in problemText:
            print(line)
示例#13
0
def languageStep():
    cfg = getConfig()
    lang = cfg.get("kat", "language")
    allLangs = set(x.lower() for x in cfg["File associations"].values())
    iter(cfg["Run commands"])
    print('Choose your language')
    print('This tool works best with', ', '.join(cfg["Run commands"]))
    print(
        'It also supports every language on Kattis, but you would need to tinker with the configurations to test optimally.'
    )
    print('(These are', ', '.join(allLangs), ')')
    print('Leave blank for', lang)
    language = input('Your pick: ')
    cfg.set("kat", "language",
            language if language.lower() in allLangs else lang)
    return True
示例#14
0
文件: submit.py 项目: hojelse/Kat
def submitCommand(args, options):
    problemName = args[0]
    directory = os.path.join(os.getcwd(), problemName)

    if not os.path.exists(problemName):
        promptToFetch(args, options)
        return Response.Error

    # if programFile is not given, we will attempt to guess it
    programFile = (formatProgramFile(args[1])
                   if args[1:] else selectProgramFile(problemName))

    if programFile == -1:
        raise Exception("Could not guess programFile")

    if "force" not in options:
        response = confirm(problemName, programFile)
        if not response: return Response.Aborted

    config = getConfig()

    session = requests.Session()

    print("📨 Submitting " + problemName + "...")

    id = postSubmission(config, session, problemName, programFile)

    print("📬 Submission Successful (url https://open.kattis.com/submissions/" +
          id + ")")

    if id == -1:
        return False

    response = Response.Failure
    try:
        response = printUntilDone(id, problemName, config, session, options)
    except:
        pass
    if "sound" in options:
        if response == Response.Success:
            winsound()
        elif response == Response.Failure:
            losesound()
    if response == Response.Success:
        if "archive" in options:
            archiveCommand(problemName, options, ".solved/")
    return response
示例#15
0
def createBoilerplate(problemName):
    from helpers.programSelector import formatCommand, guessLanguage, formatProgramFile
    cfg = getConfig()
    lang = cfg.get("kat", "language")
    if lang in cfg["Initialize commands"]:
        cmd = cfg["Initialize commands"].getcommand(lang)
        subprocess.run([p for p in cmd], cwd=problemName)
        return
    directory = os.path.dirname(os.path.realpath(__file__)) + "/../boilerplate"
    boilerplates = {
        guessLanguage(formatProgramFile(f)): f for f in os.listdir(directory) if os.path.isfile(os.path.join(directory, f))
    }
    if lang in boilerplates:
        boilerplate = boilerplates[lang]
        fileType = "." + boilerplates[lang].split(".")[-1]
        shutil.copy2(
            directory + "/" + boilerplate,
            problemName + "/" + problemName + fileType,
        )
    else:
        fileType = [file for (file, k) in cfg["File associations"].items() if k.lower() == lang.lower()]
        open(problemName + "/" + problemName + fileType[0], "a").close()
示例#16
0
import os, re, subprocess

from helpers.fileutils import getBytesFromFile
from helpers.config import getConfig

# import os, subprocess, re

cfg = getConfig()

_LANGUAGE_GUESS = cfg["File associations"]

_LANGUAGE_RUN_COMMANDS = cfg["Run commands"]

_LANGUAGE_COMPILE_COMMANDS = cfg["Compile commands"]


def selectProgramFile(problemName):
    # Get all files, and format them
    files = [
        formatProgramFile(os.path.join(problemName, f)) for f in os.listdir(problemName)
    ]
    # ..but only select those which we support
    files = list(filter(isValidProgramFile, files))

    if len(files) == 0:
        print(
            "No source file fould for problem '"
            + problemName
            + "'.\nCreate a file inside the folder matching the problem (for example '"
            + problemName
            + "/answer.py')"