time_out.time_limit errors if a function call lasts too long

This commit is contained in:
JJJHolscher 2023-07-01 14:13:04 +02:00
parent 855bb106a0
commit abbb64d8a1
7 changed files with 81 additions and 19 deletions

18
.gitignore vendored Normal file
View File

@ -0,0 +1,18 @@
# JO3'S DEFAULT IGNORE RULES
/tmp*
## ctags
/tags
/tags.temp
/tags.lock
## python
/build/
/dist/
/*.egg-info/
/.venv/
__pycache__
**.egg-info/
**.ipynb_checkpoints
## rust
/target/

1
jo3util Symbolic link
View File

@ -0,0 +1 @@
./src

View File

@ -1,7 +1,7 @@
[project] [project]
name = "NAME" name = "jo3util"
version = "0.0.0" # TODO; automatically update versions by looking at git version = "0.0.2"
description = "" description = ""
dependencies = [] dependencies = []
dynamic = ["readme"] dynamic = ["readme"]
@ -16,7 +16,7 @@ classifiers = [
github = "JJJHolscher" github = "JJJHolscher"
[project.urls] [project.urls]
homepage = "https://github.com/JJJHolscher/NAME" homepage = "https://github.com/JJJHolscher/jo3util"
[[project.authors]] [[project.authors]]
name = "Jochem Hölscher" name = "Jochem Hölscher"
@ -29,7 +29,7 @@ requires = [
build-backend = "setuptools.build_meta" build-backend = "setuptools.build_meta"
[tool.setuptools.packages.find] [tool.setuptools.packages.find]
include = ["NAME"] include = ["jo3util"]
[tool.setuptools.dynamic] [tool.setuptools.dynamic]
readme = {file = ["README.md"], content-type = "text/markdown"} readme = {file = ["README.md"], content-type = "text/markdown"}

35
src/time_out.py Normal file
View File

@ -0,0 +1,35 @@
#! /usr/bin/env python3
# vim:fenc=utf-8
"""
This code is copied from https://stackoverflow.com/questions/366682/how-to-limit-execution-time-of-a-function-call/601168#601168
"""
import signal
from contextlib import contextmanager
class TimeoutException(Exception):
pass
@contextmanager
def time_limit(seconds):
"""
## Usage
try:
with time_limit(10):
long_function_call()
except TimeoutException as e:
print("Timed out!")
"""
def signal_handler(signum, frame):
raise TimeoutException("Timed out!")
signal.signal(signal.SIGALRM, signal_handler)
signal.alarm(seconds)
try:
yield
finally:
signal.alarm(0)

View File

@ -1 +1 @@
from .test_main import * from .test_time_out import *

View File

@ -1,14 +0,0 @@
#! /usr/bin/env python3
# vim:fenc=utf-8
import unittest
from src.main import *
class TestMain(unittest.TestCase):
def test_main(self):
self.assertEqual(UNITTESTS(), 0)
if __name__ == "__main__":
unittest.main()

22
tests/test_time_out.py Normal file
View File

@ -0,0 +1,22 @@
#! /usr/bin/env python3
# vim:fenc=utf-8
import time
import unittest
from src.time_out import TimeoutException, time_limit
class TestTimeOut(unittest.TestCase):
def test_exception(self):
with self.assertRaises(TimeoutException):
with time_limit(1):
time.sleep(2)
def test_no_exception(self):
with time_limit(1):
time.sleep(0.5)
if __name__ == "__main__":
unittest.main()