Skip to content

Commit e6d6d74

Browse files
authored

File tree

16 files changed

+148
-80
lines changed

16 files changed

+148
-80
lines changed

CHANGES

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,25 @@ $ pipx install --suffix=@next 'vcspull' --pip-args '\--pre' --force
3131

3232
- `dir` -> `path` (#435)
3333

34+
### Development
35+
36+
- Strengthen linting (#436)
37+
38+
- Add flake8-commas (COM)
39+
40+
- https://docs.astral.sh/ruff/rules/#flake8-commas-com
41+
- https://pypi.org/project/flake8-commas/
42+
43+
- Add flake8-builtins (A)
44+
45+
- https://docs.astral.sh/ruff/rules/#flake8-builtins-a
46+
- https://pypi.org/project/flake8-builtins/
47+
48+
- Add flake8-errmsg (EM)
49+
50+
- https://docs.astral.sh/ruff/rules/#flake8-errmsg-em
51+
- https://pypi.org/project/flake8-errmsg/
52+
3453
### Documentation
3554

3655
- Refactor API docs to split across multiple pages (#431)

conftest.py

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,8 @@ def xdg_config_path(
5858

5959
@pytest.fixture(scope="function")
6060
def config_path(
61-
xdg_config_path: pathlib.Path, request: pytest.FixtureRequest
61+
xdg_config_path: pathlib.Path,
62+
request: pytest.FixtureRequest,
6263
) -> pathlib.Path:
6364
"""Ensure and return vcspull configuration path."""
6465
conf_path = xdg_config_path / "vcspull"
@@ -73,7 +74,8 @@ def clean() -> None:
7374

7475
@pytest.fixture(autouse=True)
7576
def set_xdg_config_path(
76-
monkeypatch: pytest.MonkeyPatch, xdg_config_path: pathlib.Path
77+
monkeypatch: pytest.MonkeyPatch,
78+
xdg_config_path: pathlib.Path,
7779
) -> None:
7880
"""Set XDG_CONFIG_HOME environment variable."""
7981
monkeypatch.setenv("XDG_CONFIG_HOME", str(xdg_config_path))
@@ -82,11 +84,11 @@ def set_xdg_config_path(
8284
@pytest.fixture(scope="function")
8385
def repos_path(user_path: pathlib.Path, request: pytest.FixtureRequest) -> pathlib.Path:
8486
"""Return temporary directory for repository checkout guaranteed unique."""
85-
dir = user_path / "repos"
86-
dir.mkdir(exist_ok=True)
87+
path = user_path / "repos"
88+
path.mkdir(exist_ok=True)
8789

8890
def clean() -> None:
89-
shutil.rmtree(dir)
91+
shutil.rmtree(path)
9092

9193
request.addfinalizer(clean)
92-
return dir
94+
return path

docs/conf.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@
5353
master_doc = "index"
5454

5555
project = about["__title__"]
56-
copyright = about["__copyright__"]
56+
project_copyright = about["__copyright__"]
5757

5858
version = "%s" % (".".join(about["__version__"].split("."))[:2])
5959
release = "%s" % (about["__version__"])
@@ -96,7 +96,7 @@
9696
"sidebar/navigation.html",
9797
"sidebar/projects.html",
9898
"sidebar/scroll-end.html",
99-
]
99+
],
100100
}
101101

102102
# linkify_issues

pyproject.toml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -150,8 +150,11 @@ select = [
150150
"F", # pyflakes
151151
"I", # isort
152152
"UP", # pyupgrade
153+
"A", # flake8-builtins
153154
"B", # flake8-bugbear
154155
"C4", # flake8-comprehensions
156+
"COM", # flake8-commas
157+
"EM", # flake8-errmsg
155158
"Q", # flake8-quotes
156159
"PTH", # flake8-use-pathlib
157160
"SIM", # flake8-simplify
@@ -160,6 +163,9 @@ select = [
160163
"RUF", # Ruff-specific rules
161164
"D", # pydocstyle
162165
]
166+
ignore = [
167+
"COM812", # missing trailing comma, ruff format conflict
168+
]
163169

164170
[tool.ruff.lint.pydocstyle]
165171
convention = "numpy"

scripts/generate_gitlab.py

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@
2020

2121
parser = argparse.ArgumentParser(
2222
description="Script to generate vcsconfig for all repositories \
23-
under the given namespace (needs Gitlab >= 10.3)"
23+
under the given namespace (needs Gitlab >= 10.3)",
2424
)
2525
parser.add_argument("gitlab_host", type=str, help="url to the gitlab instance")
2626
parser.add_argument(
@@ -47,14 +47,14 @@
4747
result = input(
4848
"The target config file (%s) already exists, \
4949
do you want to overwrite it? [y/N] "
50-
% (config_filename)
50+
% (config_filename),
5151
)
5252

5353
if result != "y":
5454
print(
5555
"Aborting per user request as existing config file (%s) \
5656
should not be overwritten!"
57-
% (config_filename)
57+
% (config_filename),
5858
)
5959
sys.exit(0)
6060

@@ -103,7 +103,7 @@
103103
name="origin",
104104
fetch_url=f"ssh://{url_to_repo}",
105105
push_url=f"ssh://{url_to_repo}",
106-
)
106+
),
107107
},
108108
"vcs": vcs,
109109
}

src/vcspull/_internal/config_reader.py

Lines changed: 19 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ def __init__(self, content: "RawConfigData") -> None:
2626
self.content = content
2727

2828
@staticmethod
29-
def _load(format: "FormatLiteral", content: str) -> dict[str, t.Any]:
29+
def _load(fmt: "FormatLiteral", content: str) -> dict[str, t.Any]:
3030
"""Load raw config data and directly return it.
3131
3232
>>> ConfigReader._load("json", '{ "session_name": "my session" }')
@@ -35,21 +35,22 @@ def _load(format: "FormatLiteral", content: str) -> dict[str, t.Any]:
3535
>>> ConfigReader._load("yaml", 'session_name: my session')
3636
{'session_name': 'my session'}
3737
"""
38-
if format == "yaml":
38+
if fmt == "yaml":
3939
return t.cast(
4040
dict[str, t.Any],
4141
yaml.load(
4242
content,
4343
Loader=yaml.SafeLoader,
4444
),
4545
)
46-
elif format == "json":
46+
elif fmt == "json":
4747
return t.cast(dict[str, t.Any], json.loads(content))
4848
else:
49-
raise NotImplementedError(f"{format} not supported in configuration")
49+
msg = f"{fmt} not supported in configuration"
50+
raise NotImplementedError(msg)
5051

5152
@classmethod
52-
def load(cls, format: "FormatLiteral", content: str) -> "ConfigReader":
53+
def load(cls, fmt: "FormatLiteral", content: str) -> "ConfigReader":
5354
"""Load raw config data into a ConfigReader instance (to dump later).
5455
5556
>>> cfg = ConfigReader.load("json", '{ "session_name": "my session" }')
@@ -66,7 +67,7 @@ def load(cls, format: "FormatLiteral", content: str) -> "ConfigReader":
6667
"""
6768
return cls(
6869
content=cls._load(
69-
format=format,
70+
fmt=fmt,
7071
content=content,
7172
),
7273
)
@@ -105,14 +106,15 @@ def _from_file(cls, path: pathlib.Path) -> dict[str, t.Any]:
105106
content = path.open().read()
106107

107108
if path.suffix in [".yaml", ".yml"]:
108-
format: "FormatLiteral" = "yaml"
109+
fmt: "FormatLiteral" = "yaml"
109110
elif path.suffix == ".json":
110-
format = "json"
111+
fmt = "json"
111112
else:
112-
raise NotImplementedError(f"{path.suffix} not supported in {path}")
113+
msg = f"{path.suffix} not supported in {path}"
114+
raise NotImplementedError(msg)
113115

114116
return cls._load(
115-
format=format,
117+
fmt=fmt,
116118
content=content,
117119
)
118120

@@ -158,7 +160,7 @@ def from_file(cls, path: pathlib.Path) -> "ConfigReader":
158160

159161
@staticmethod
160162
def _dump(
161-
format: "FormatLiteral",
163+
fmt: "FormatLiteral",
162164
content: "RawConfigData",
163165
indent: int = 2,
164166
**kwargs: t.Any,
@@ -171,22 +173,23 @@ def _dump(
171173
>>> ConfigReader._dump("json", { "session_name": "my session" })
172174
'{\n "session_name": "my session"\n}'
173175
"""
174-
if format == "yaml":
176+
if fmt == "yaml":
175177
return yaml.dump(
176178
content,
177179
indent=2,
178180
default_flow_style=False,
179181
Dumper=yaml.SafeDumper,
180182
)
181-
elif format == "json":
183+
elif fmt == "json":
182184
return json.dumps(
183185
content,
184186
indent=2,
185187
)
186188
else:
187-
raise NotImplementedError(f"{format} not supported in config")
189+
msg = f"{fmt} not supported in config"
190+
raise NotImplementedError(msg)
188191

189-
def dump(self, format: "FormatLiteral", indent: int = 2, **kwargs: t.Any) -> str:
192+
def dump(self, fmt: "FormatLiteral", indent: int = 2, **kwargs: t.Any) -> str:
190193
r"""Dump via ConfigReader instance.
191194
192195
>>> cfg = ConfigReader({ "session_name": "my session" })
@@ -196,7 +199,7 @@ def dump(self, format: "FormatLiteral", indent: int = 2, **kwargs: t.Any) -> str
196199
'{\n "session_name": "my session"\n}'
197200
"""
198201
return self._dump(
199-
format=format,
202+
fmt=fmt,
200203
content=self.content,
201204
indent=indent,
202205
**kwargs,

src/vcspull/cli/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@
2323
vcspull sync "django-*" flask
2424
vcspull sync -c ./myrepos.yaml "*"
2525
vcspull sync -c ./myrepos.yaml myproject
26-
"""
26+
""",
2727
).strip()
2828

2929

src/vcspull/config.py

Lines changed: 12 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -116,13 +116,16 @@ def extract_repos(
116116
continue
117117
if isinstance(url, str):
118118
conf["remotes"][remote_name] = GitRemote(
119-
name=remote_name, fetch_url=url, push_url=url
119+
name=remote_name,
120+
fetch_url=url,
121+
push_url=url,
120122
)
121123
elif isinstance(url, dict):
122124
assert "push_url" in url
123125
assert "fetch_url" in url
124126
conf["remotes"][remote_name] = GitRemote(
125-
name=remote_name, **url
127+
name=remote_name,
128+
**url,
126129
)
127130

128131
def is_valid_config_dict(val: t.Any) -> "TypeGuard[ConfigDict]":
@@ -153,7 +156,7 @@ def find_home_config_files(
153156
log.debug(
154157
"No config file found. Create a .vcspull.yaml or .vcspull.json"
155158
" in your $HOME directory. http://vcspull.git-pull.com for a"
156-
" quickstart."
159+
" quickstart.",
157160
)
158161
else:
159162
if sum(filter(None, [has_json_config, has_yaml_config])) > 1:
@@ -280,7 +283,8 @@ def load_configs(
280283

281284

282285
def detect_duplicate_repos(
283-
config1: list["ConfigDict"], config2: list["ConfigDict"]
286+
config1: list["ConfigDict"],
287+
config2: list["ConfigDict"],
284288
) -> list[ConfigDictTuple]:
285289
"""Return duplicate repos dict if repo_dir same and vcs different.
286290
@@ -379,7 +383,7 @@ def filter_repos(
379383
r
380384
for r in config
381385
if fnmatch.fnmatch(str(pathlib.Path(r["path"]).parent), str(path))
382-
]
386+
],
383387
)
384388

385389
if vcs_url:
@@ -391,14 +395,15 @@ def filter_repos(
391395

392396
if name:
393397
repo_list.extend(
394-
[r for r in config if fnmatch.fnmatch(str(r.get("name")), name)]
398+
[r for r in config if fnmatch.fnmatch(str(r.get("name")), name)],
395399
)
396400

397401
return repo_list
398402

399403

400404
def is_config_file(
401-
filename: str, extensions: t.Optional[t.Union[list[str], str]] = None
405+
filename: str,
406+
extensions: t.Optional[t.Union[list[str], str]] = None,
402407
) -> bool:
403408
"""Return True if file has a valid config file type.
404409

src/vcspull/log.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -164,7 +164,7 @@ def template(self, record: logging.LogRecord) -> str:
164164
]
165165

166166
tpl = "".join(
167-
reset + levelname + asctime + name + module_funcName + lineno + reset
167+
reset + levelname + asctime + name + module_funcName + lineno + reset,
168168
)
169169

170170
return tpl
@@ -176,7 +176,7 @@ class RepoLogFormatter(LogFormatter):
176176
def template(self, record: logging.LogRecord) -> str:
177177
"""Template for logging vcs bin name, along with a contextual hint."""
178178
record.message = "".join(
179-
[Fore.MAGENTA, Style.BRIGHT, record.message, Fore.RESET, Style.RESET_ALL]
179+
[Fore.MAGENTA, Style.BRIGHT, record.message, Fore.RESET, Style.RESET_ALL],
180180
)
181181
return "{}|{}| {}({}) {}".format(
182182
Fore.GREEN + Style.DIM,

tests/fixtures/example.py

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@
2121
"upstream": "git+https://github.com/emre/kaptan",
2222
"ms": "git+https://github.com/ms/kaptan.git",
2323
},
24-
}
24+
},
2525
},
2626
"/home/me/myproject": {
2727
".vim": {
@@ -31,7 +31,7 @@
3131
".tmux": {
3232
"url": "git+git@github.com:tony/tmux-config.git",
3333
"shell_command_after": [
34-
"ln -sf /home/me/.tmux/.tmux.conf /home/me/.tmux.conf"
34+
"ln -sf /home/me/.tmux/.tmux.conf /home/me/.tmux.conf",
3535
],
3636
},
3737
},
@@ -73,14 +73,14 @@
7373
"name": "upstream",
7474
"fetch_url": "git+https://github.com/emre/kaptan",
7575
"push_url": "git+https://github.com/emre/kaptan",
76-
}
76+
},
7777
),
7878
"ms": GitRemote(
7979
**{
8080
"name": "ms",
8181
"fetch_url": "git+https://github.com/ms/kaptan.git",
8282
"push_url": "git+https://github.com/ms/kaptan.git",
83-
}
83+
},
8484
),
8585
},
8686
},

0 commit comments

Comments
 (0)