Skip to content

Commit bb928bf

Browse files
committed
fix lint
1 parent bd58b6c commit bb928bf

15 files changed

Lines changed: 146 additions & 712 deletions

.pylintrc

Lines changed: 0 additions & 643 deletions
This file was deleted.

mypy.ini

Lines changed: 0 additions & 19 deletions
This file was deleted.

pyproject.toml

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,3 +36,52 @@ dependencies = [
3636
[build-system]
3737
requires = ["uv_build>=0.8.10,<0.9.0"]
3838
build-backend = "uv_build"
39+
40+
[tool.pylint.messages_control]
41+
disable = [
42+
"raw-checker-failed",
43+
"bad-inline-option",
44+
"locally-disabled",
45+
"file-ignored",
46+
"suppressed-message",
47+
"useless-suppression",
48+
"deprecated-pragma",
49+
"use-symbolic-message-instead",
50+
"logging-fstring-interpolation",
51+
"unused-import",
52+
"ungrouped-imports",
53+
"subprocess-run-check",
54+
"too-many-instance-attributes",
55+
"missing-module-docstring",
56+
"unnecessary-ellipsis", # pylint cannot work with typed Protocol,
57+
"too-many-arguments",
58+
"too-many-locals",
59+
"too-many-positional-arguments",
60+
"too-many-statements",
61+
"unspecified-encoding",
62+
"missing-class-docstring",
63+
]
64+
fail-under = 9
65+
max-line-length = 120
66+
67+
[tool.pylint.typecheck]
68+
generated-members = ["cv2.*", "skimage.metrics.*"]
69+
70+
[tool.mypy]
71+
python_version = "3.11"
72+
warn_return_any = true
73+
warn_unused_configs = true
74+
ignore_missing_imports = true
75+
check_untyped_defs = true
76+
allow_redefinition = false
77+
ignore_errors = false
78+
implicit_reexport = false
79+
local_partial_types = true
80+
no_implicit_optional = true
81+
strict_equality = true
82+
strict_optional = true
83+
warn_no_return = true
84+
warn_redundant_casts = true
85+
warn_unreachable = true
86+
warn_unused_ignores = false
87+
plugins = ["returns.contrib.mypy.returns_plugin"]

src/tfbench/add_dependency.py

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,18 @@
1+
import json
2+
from typing import Iterable
3+
14
import fire
2-
import funcy
35
from funcy_chain import Chain
4-
import logging
5-
import json
66
from dacite import from_dict
7+
78
from tfbench.common import extract_function_name
89
from tfbench.hs_parser import HASKELL_LANGUAGE
910
from tfbench.hs_parser.ast_util import AST
1011
from tfbench.common import BenchmarkTask
11-
from typing import Iterable
1212

1313

1414
def build_dependency_dict(tasks: list[BenchmarkTask]) -> dict[str, str]:
15+
"""dependency mapping from function names to their signatures"""
1516
return {
1617
fn_name: t.signature
1718
for t in tasks
@@ -48,6 +49,7 @@ def get_func_calls(task: BenchmarkTask) -> set[str]:
4849

4950

5051
def _is_input(code: str, call: str) -> bool:
52+
"""check if a function call is an input to the task"""
5153
inputs: list[list[str]] = (
5254
Chain(code.splitlines())
5355
.filter(lambda l: "=" in l)
@@ -60,6 +62,8 @@ def _is_input(code: str, call: str) -> bool:
6062

6163

6264
def add_dependencies(dependency_dict: dict[str, str]):
65+
"""add dependencies to benchmark tasks"""
66+
6367
def add_for_task(task: BenchmarkTask) -> BenchmarkTask:
6468
calls: Iterable[str] = get_func_calls(task)
6569
calls = filter(lambda c: not _is_input(task.code, c), calls)
@@ -73,6 +77,7 @@ def main(
7377
input_file: str = "data/source/base-4.20.0.0.jsonl",
7478
output_file: str = "out.jsonl",
7579
):
80+
"""add dependency to a task json file"""
7681
with open(input_file, "r") as fp:
7782
tasks: list[BenchmarkTask] = (
7883
Chain(fp.readlines())

src/tfbench/common.py

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
11
from dataclasses import dataclass, field
22
import re
33
import copy
4-
from funcy import lmap
54
import sys
65
import io
76

7+
from funcy import lmap
88
import markdown_to_json
99

1010
# Default hyper-parameters
@@ -40,10 +40,16 @@ class BenchmarkTask:
4040

4141

4242
def extract_function_name(task: BenchmarkTask) -> str | None:
43+
"""get function name from a task
44+
For example, given a task with signature 'foo :: Int -> Int',
45+
it will return 'foo'.
46+
"""
4347
return task.signature.split("::")[0].strip()
4448

4549

4650
def clean_tab_spaces(task: BenchmarkTask) -> BenchmarkTask:
51+
"""remove tab spaces from the code"""
52+
4753
def clean(s: str) -> str:
4854
return re.sub(r"[ \t]+", " ", s)
4955

@@ -56,6 +62,7 @@ def clean(s: str) -> str:
5662

5763

5864
def remove_comments(code: str) -> str:
65+
"""remove Haskell comments"""
5966
# multi-line
6067
# code = re.sub(r"\{\-[\s\S]*?\-\}", "", code)
6168
code = re.sub(r"\{\-.*?\-\}", "", code, flags=re.DOTALL)
@@ -65,6 +72,7 @@ def remove_comments(code: str) -> str:
6572

6673

6774
def get_sys_prompt(pure: bool) -> str:
75+
"""helper function to get system prompt for pure version of TF-Bench"""
6876
sys_prompt = SYSTEM_PROMPT + INSTRUCT_PROMPT
6977
sys_prompt += PURE_PROMPT if pure else CORE_PROMPT
7078
return sys_prompt
@@ -99,9 +107,9 @@ def remove_return_type(sig: str) -> str:
99107
# Keep '->' and discard what follows
100108
new_type = type_part[: last_arrow_index + 2]
101109
return func_part + " " + new_type.rstrip()
102-
else:
103-
# No top-level arrow found; return as-is
104-
return sig
110+
111+
# No top-level arrow found; return as-is
112+
return sig
105113

106114

107115
def get_prompt(task: BenchmarkTask) -> str:

src/tfbench/dataset.py

Lines changed: 11 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,25 @@
11
"""main script to build Haskell dataset"""
22

3+
from enum import IntEnum
4+
import os
5+
import logging
6+
import json
7+
38
import fire
49
from returns.result import Success, Failure
510
from returns.io import IOResult, IOSuccess, IOFailure
611
from funcy_chain import Chain
7-
import os
8-
import logging
9-
from enum import IntEnum
10-
import json
1112
from tqdm import tqdm
1213
from funcy import lmap
14+
1315
from tfbench.hs_parser import HASKELL_LANGUAGE
1416
from tfbench.hs_parser.ast_util import AST, HaskellFunction
15-
from tfbench.hs_parser.polymorphism import get_polymorphic_type, PolymorphicType
17+
from tfbench.hs_parser.polymorphism import get_polymorphic_type
1618
from tfbench.common import remove_comments
1719

1820

1921
def wrap_repo(s: str) -> str:
20-
# NOTE: this is a placeholder function
21-
# the implementation depends on how the repo is downloaded
22-
# please refer to HMTypes4Py repo
22+
"""NOTE: this is a placeholder function"""
2323
return s
2424

2525

@@ -44,6 +44,7 @@ def collect_hs_files(root: str):
4444

4545

4646
def collect_from_file(file_path: str) -> list[dict[str, str]]:
47+
"""extract benchmark tasks from a Haskell file"""
4748
with open(file_path, "r", errors="replace") as fp:
4849
code = fp.read()
4950

@@ -66,6 +67,7 @@ def _to_json(func: HaskellFunction) -> dict[str, str]:
6667
def collect_from_repo(
6768
repo_id: str, repo_root: str, source_root: str
6869
) -> IOResult[int, CollectionErrorCode]:
70+
"""Collect all tasks from a Haskell repository"""
6971
repo_path = os.path.join(repo_root, wrap_repo(repo_id))
7072
if not os.path.exists(repo_path) or not os.path.isdir(repo_path):
7173
return IOFailure(CollectionErrorCode.REPO_NOT_FOUND)
@@ -98,6 +100,7 @@ def main(
98100
repo_root: str = "data/repos",
99101
oroot: str = "data/source",
100102
):
103+
"""script to extract benchmark tasks from Haskell repositories"""
101104
with open(input_repo_list_path) as fp:
102105
repo_id_list = [l.strip() for l in fp.readlines()]
103106

src/tfbench/evaluation.py

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,15 @@
1-
import fire
21
import json
32
import logging
4-
from tfbench.common import BenchmarkTask
5-
from tfbench.postprocessing import postprocess, TASK_STRATEGIES, RESPONSE_STRATEGIES
6-
from funcy_chain import Chain
7-
from dacite import from_dict
83
from itertools import starmap
94
import re
105

6+
import fire
7+
from funcy_chain import Chain
8+
from dacite import from_dict
9+
10+
from tfbench.common import BenchmarkTask
11+
from tfbench.postprocessing import postprocess, TASK_STRATEGIES, RESPONSE_STRATEGIES
12+
1113

1214
def tokenize_type_signature(sig: str) -> list[str]:
1315
"""
@@ -64,6 +66,7 @@ def alpha_equiv(s1: str, s2: str) -> bool:
6466

6567

6668
def evaluate_one_task(task: BenchmarkTask, result: str) -> bool:
69+
"""evaluate a single task against its result by alpha equivalence"""
6770
ground_truth = postprocess(task.signature, TASK_STRATEGIES)
6871
result = postprocess(result, RESPONSE_STRATEGIES)
6972
return alpha_equiv(ground_truth, result)
@@ -72,6 +75,7 @@ def evaluate_one_task(task: BenchmarkTask, result: str) -> bool:
7275
def evaluate(
7376
benchmark_f: list[BenchmarkTask], results: list[str]
7477
) -> dict[str, int | float]:
78+
"""evaluate all generation results"""
7579

7680
assert len(benchmark_f) == len(results)
7781
eval_results = starmap(evaluate_one_task, zip(benchmark_f, results))
@@ -89,6 +93,7 @@ def main(
8993
benchmark_file: str = "Benchmark-F.jsonl",
9094
results_file: str = "data/experiment/gpt_generated_responses.jsonl",
9195
):
96+
"""script to run all evaluation tasks"""
9297
with open(benchmark_file, "r") as file:
9398
benchmark_f: list[BenchmarkTask] = (
9499
Chain(file.readlines())

src/tfbench/experiment.py

Lines changed: 16 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,10 @@
22
Experiment script for OpenAI models
33
"""
44

5-
from openai import OpenAI
6-
from anthropic import Anthropic, InternalServerError
75
from typing import Callable
86

7+
from openai import OpenAI
8+
from anthropic import Anthropic, InternalServerError
99
from google import genai
1010
from google.genai.types import GenerateContentConfig, ThinkingConfig
1111

@@ -64,6 +64,8 @@ def get_oai_ttc_model(
6464
model: str = "o1-preview-2024-09-12",
6565
pure: bool = False,
6666
) -> Callable[[str], str | None]:
67+
"""OpenAI Reasoning Models"""
68+
6769
def generate_type_signature(prompt: str) -> str | None:
6870
completion = client.chat.completions.create(
6971
messages=[
@@ -83,6 +85,8 @@ def get_oai_model(
8385
model: str = "gpt-3.5-turbo",
8486
pure: bool = False,
8587
) -> Callable[[str], str | None]:
88+
"""Regular OpenAI Models"""
89+
8690
def generate_type_signature(prompt: str) -> str | None:
8791
completion = client.chat.completions.create(
8892
messages=[
@@ -107,6 +111,8 @@ def get_ant_ttc_model(
107111
pure: bool = False,
108112
thinking_budget: int = 1024,
109113
) -> Callable[[str], str | None]:
114+
"Claude Reasoning Models"
115+
110116
def generate_type_signature(prompt: str) -> str | None:
111117
try:
112118
message = client.beta.messages.create(
@@ -138,6 +144,8 @@ def get_ant_model(
138144
model: str = "claude-3-5-sonnet-20240620",
139145
pure: bool = False,
140146
) -> Callable[[str], str | None]:
147+
"""Claude regular Models"""
148+
141149
def generate_type_signature(prompt: str) -> str | None:
142150
try:
143151
message = client.messages.create(
@@ -155,8 +163,8 @@ def generate_type_signature(prompt: str) -> str | None:
155163
if len(contents) > 0:
156164
text = contents[0].text # type: ignore
157165
return text if isinstance(text, str) else None
158-
else:
159-
return None
166+
167+
return None
160168

161169
return generate_type_signature
162170

@@ -166,6 +174,8 @@ def get_gemini_model(
166174
model: str = "gemini-2.0-flash-lite",
167175
pure: bool = False,
168176
) -> Callable[[str], str | None]:
177+
"""Gemini Models"""
178+
169179
def generate_type_signature(prompt: str) -> str | None:
170180
response = client.models.generate_content(
171181
model=model,
@@ -185,6 +195,8 @@ def get_gemini_ttc_model(
185195
pure: bool = False,
186196
thinking_budget: int = 1024,
187197
) -> Callable[[str], str | None]:
198+
"""Gemini Reasoning Models"""
199+
188200
def generate_type_signature(prompt: str) -> str | None:
189201
response = client.models.generate_content(
190202
model=model,

src/tfbench/experiment_ollama.py

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,8 @@
22
Experiment script for OSS models using Ollama
33
"""
44

5-
from ollama import Client as OllamaClient, ResponseError
65
from typing import Union
6+
from ollama import Client as OllamaClient, ResponseError
77
from tfbench.common import get_sys_prompt
88

99
OLLAMA_OSS = [
@@ -61,15 +61,17 @@ def get_ollama_model(
6161
Parameters:
6262
client (OllamaClient): The Ollama client instance used for sending requests to the model.
6363
64-
model (str): Name of the model to use for generating type signatures. Must be one of the predefined models in OLLAMA_MODELS.
65-
Default is "llama3:8b".
64+
model (str): Name of the model to use for generating type signatures.
65+
Must be one of the predefined models in OLLAMA_MODELS.
66+
Default is "llama3:8b".
6667
6768
pure (bool): If True, uses the original variable naming in type inference.
6869
If False, uses rewritten variable naming (e.g., `v1`, `v2`, ...). Default is False.
6970
7071
Returns:
71-
Callable[[str], Union[str, None]]: A function that takes a prompt string as input and returns the generated type
72-
signature as a string, or None if the generation fails.
72+
Callable[[str], Union[str, None]]:
73+
A function that takes a prompt string as input and returns the generated type
74+
signature as a string, or None if the generation fails.
7375
"""
7476

7577
def generate_type_signature(prompt: str) -> Union[str, None]:

0 commit comments

Comments
 (0)