1
1
"""Development tasks."""
2
2
3
+ import importlib
3
4
import os
4
5
import re
5
6
import sys
6
- from functools import wraps
7
+ from io import StringIO
7
8
from pathlib import Path
8
- from shutil import which
9
9
from typing import List , Optional , Pattern
10
10
from urllib .request import urlopen
11
11
@@ -43,7 +43,6 @@ def update_changelog(
43
43
marker : str ,
44
44
version_regex : str ,
45
45
template_url : str ,
46
- commit_style : str ,
47
46
) -> None :
48
47
"""
49
48
Update the given changelog file in place.
@@ -53,12 +52,16 @@ def update_changelog(
53
52
marker: The line after which to insert new contents.
54
53
version_regex: A regular expression to find currently documented versions in the file.
55
54
template_url: The URL to the Jinja template used to render contents.
56
- commit_style: The style of commit messages to parse.
57
55
"""
56
+ from git_changelog .build import Changelog
57
+ from git_changelog .commit import AngularStyle
58
+ from jinja2 .sandbox import SandboxedEnvironment
59
+
60
+ AngularStyle .DEFAULT_RENDER .insert (0 , AngularStyle .TYPES ["build" ])
58
61
env = SandboxedEnvironment (autoescape = False )
59
62
template_text = urlopen (template_url ).read ().decode ("utf8" ) # noqa: S310
60
63
template = env .from_string (template_text )
61
- changelog = Changelog ("." , style = commit_style )
64
+ changelog = Changelog ("." , style = "angular" )
62
65
63
66
if len (changelog .versions_list ) == 1 :
64
67
last_version = changelog .versions_list [0 ]
@@ -98,14 +101,13 @@ def changelog(ctx):
98
101
"marker" : "<!-- insertion marker -->" ,
99
102
"version_regex" : r"^## \[v?(?P<version>[^\]]+)" ,
100
103
"template_url" : template_url ,
101
- "commit_style" : "angular" ,
102
104
},
103
105
title = "Updating changelog" ,
104
106
pty = PTY ,
105
107
)
106
108
107
109
108
- @duty (pre = ["check_code_quality " , "check_types" , "check_docs" , "check_dependencies" ])
110
+ @duty (pre = ["check_quality " , "check_types" , "check_docs" , "check_dependencies" ])
109
111
def check (ctx ):
110
112
"""
111
113
Check it all!
@@ -116,7 +118,7 @@ def check(ctx):
116
118
117
119
118
120
@duty
119
- def check_code_quality (ctx , files = PY_SRC ):
121
+ def check_quality (ctx , files = PY_SRC ):
120
122
"""
121
123
Check the code quality.
122
124
@@ -135,49 +137,48 @@ def check_dependencies(ctx):
135
137
Arguments:
136
138
ctx: The context instance (passed automatically).
137
139
"""
138
- nofail = False
139
- safety = which ("safety" )
140
- if not safety :
141
- pipx = which ("pipx" )
142
- if pipx :
143
- safety = f"{ pipx } run safety"
144
- else :
145
- safety = "safety"
146
- nofail = True
147
- ctx .run (
148
- f"pdm export -f requirements --without-hashes | { safety } check --stdin --full-report" ,
149
- title = "Checking dependencies" ,
150
- pty = PTY ,
151
- nofail = nofail ,
140
+ # undo possible patching
141
+ # see https://github.com/pyupio/safety/issues/348
142
+ for module in sys .modules : # noqa: WPS528
143
+ if module .startswith ("safety." ) or module == "safety" :
144
+ del sys .modules [module ] # noqa: WPS420
145
+
146
+ importlib .invalidate_caches ()
147
+
148
+ # reload original, unpatched safety
149
+ from safety .formatter import SafetyFormatter
150
+ from safety .safety import calculate_remediations
151
+ from safety .safety import check as safety_check
152
+ from safety .util import read_requirements
153
+
154
+ # retrieve the list of dependencies
155
+ requirements = ctx .run (
156
+ ["pdm" , "export" , "-f" , "requirements" , "--without-hashes" ],
157
+ title = "Exporting dependencies as requirements" ,
158
+ allow_overrides = False ,
152
159
)
153
160
154
-
155
- def no_docs_py36 (nofail = True ):
156
- """
157
- Decorate a duty that builds docs to warn that it's not possible on Python 3.6.
158
-
159
- Arguments:
160
- nofail: Whether to fail or not.
161
-
162
- Returns:
163
- The decorated function.
164
- """
165
-
166
- def decorator (func ):
167
- @wraps (func )
168
- def wrapper (ctx ):
169
- if sys .version_info <= (3 , 7 , 0 ):
170
- ctx .run (["false" ], title = "Docs can't be built on Python 3.6" , nofail = nofail , quiet = True )
171
- else :
172
- func (ctx )
173
-
174
- return wrapper
175
-
176
- return decorator
161
+ # check using safety as a library
162
+ def safety (): # noqa: WPS430
163
+ packages = list (read_requirements (StringIO (requirements )))
164
+ vulns , db_full = safety_check (packages = packages , ignore_vulns = "" )
165
+ remediations = calculate_remediations (vulns , db_full )
166
+ output_report = SafetyFormatter ("text" ).render_vulnerabilities (
167
+ announcements = [],
168
+ vulnerabilities = vulns ,
169
+ remediations = remediations ,
170
+ full = True ,
171
+ packages = packages ,
172
+ )
173
+ if vulns :
174
+ print (output_report )
175
+ return False
176
+ return True
177
+
178
+ ctx .run (safety , title = "Checking dependencies" )
177
179
178
180
179
181
@duty
180
- @no_docs_py36 ()
181
182
def check_docs (ctx ):
182
183
"""
183
184
Check if the documentation builds correctly.
@@ -190,8 +191,8 @@ def check_docs(ctx):
190
191
ctx .run ("mkdocs build -s" , title = "Building documentation" , pty = PTY )
191
192
192
193
193
- @duty
194
- def check_types (ctx ):
194
+ @duty # noqa: WPS231
195
+ def check_types (ctx ): # noqa: WPS231
195
196
"""
196
197
Check that the code is correctly typed.
197
198
@@ -223,7 +224,6 @@ def clean(ctx):
223
224
224
225
225
226
@duty
226
- @no_docs_py36 (nofail = False )
227
227
def docs (ctx ):
228
228
"""
229
229
Build the documentation locally.
@@ -235,7 +235,6 @@ def docs(ctx):
235
235
236
236
237
237
@duty
238
- @no_docs_py36 (nofail = False )
239
238
def docs_serve (ctx , host = "127.0.0.1" , port = 8000 ):
240
239
"""
241
240
Serve the documentation (localhost:8000).
@@ -249,7 +248,6 @@ def docs_serve(ctx, host="127.0.0.1", port=8000):
249
248
250
249
251
250
@duty
252
- @no_docs_py36 (nofail = False )
253
251
def docs_deploy (ctx ):
254
252
"""
255
253
Deploy the documentation on GitHub pages.
@@ -294,7 +292,7 @@ def release(ctx, version):
294
292
ctx .run ("git push --tags" , title = "Pushing tags" , pty = False )
295
293
ctx .run ("pdm build" , title = "Building dist/wheel" , pty = PTY )
296
294
ctx .run ("twine upload --skip-existing dist/*" , title = "Publishing version" , pty = PTY )
297
- docs_deploy .run () # type: ignore
295
+ docs_deploy .run ()
298
296
299
297
300
298
@duty (silent = True )
0 commit comments