py2docfx 0.1.9.dev1917798__py3-none-any.whl → 0.1.9.dev1926139__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (79) hide show
  1. py2docfx/__main__.py +77 -22
  2. py2docfx/convert_prepare/environment.py +34 -13
  3. py2docfx/convert_prepare/generate_document.py +12 -5
  4. py2docfx/convert_prepare/get_source.py +5 -1
  5. py2docfx/convert_prepare/git.py +24 -20
  6. py2docfx/convert_prepare/package_info.py +15 -9
  7. py2docfx/convert_prepare/pip_utils.py +29 -8
  8. py2docfx/convert_prepare/post_process/merge_toc.py +5 -1
  9. py2docfx/convert_prepare/sphinx_caller.py +31 -14
  10. py2docfx/convert_prepare/tests/test_generate_document.py +2 -0
  11. py2docfx/convert_prepare/tests/test_sphinx_caller.py +2 -0
  12. py2docfx/convert_prepare/tests/utils.py +11 -0
  13. py2docfx/docfx_yaml/build_finished.py +11 -3
  14. py2docfx/docfx_yaml/convert_class.py +4 -2
  15. py2docfx/docfx_yaml/convert_enum.py +4 -2
  16. py2docfx/docfx_yaml/convert_module.py +4 -2
  17. py2docfx/docfx_yaml/convert_package.py +4 -2
  18. py2docfx/docfx_yaml/logger.py +68 -0
  19. py2docfx/docfx_yaml/process_doctree.py +6 -4
  20. py2docfx/docfx_yaml/translator.py +5 -7
  21. py2docfx/docfx_yaml/writer.py +10 -4
  22. py2docfx/docfx_yaml/yaml_builder.py +0 -1
  23. py2docfx/venv/basevenv/Lib/site-packages/setuptools/build_meta.py +2 -2
  24. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/bdist_egg.py +1 -1
  25. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/bdist_wheel.py +25 -39
  26. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/build_ext.py +2 -2
  27. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/build_py.py +9 -14
  28. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/easy_install.py +2 -2
  29. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/editable_wheel.py +2 -2
  30. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/egg_info.py +3 -2
  31. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/install_egg_info.py +2 -2
  32. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/saveopts.py +2 -2
  33. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/sdist.py +2 -2
  34. py2docfx/venv/basevenv/Lib/site-packages/setuptools/command/setopt.py +1 -1
  35. py2docfx/venv/basevenv/Lib/site-packages/setuptools/config/pyprojecttoml.py +0 -13
  36. py2docfx/venv/basevenv/Lib/site-packages/setuptools/dist.py +3 -2
  37. py2docfx/venv/basevenv/Lib/site-packages/setuptools/monkey.py +3 -3
  38. py2docfx/venv/basevenv/Lib/site-packages/setuptools/msvc.py +11 -11
  39. py2docfx/venv/basevenv/Lib/site-packages/setuptools/tests/config/test_pyprojecttoml.py +0 -7
  40. py2docfx/venv/basevenv/Lib/site-packages/setuptools/tests/test_core_metadata.py +168 -72
  41. py2docfx/venv/basevenv/Lib/site-packages/setuptools/unicode_utils.py +3 -3
  42. py2docfx/venv/basevenv/Lib/site-packages/wheel/__init__.py +1 -1
  43. py2docfx/venv/basevenv/Lib/site-packages/wheel/cli/convert.py +1 -2
  44. py2docfx/venv/venv1/Lib/site-packages/jwt/__init__.py +3 -2
  45. py2docfx/venv/venv1/Lib/site-packages/jwt/algorithms.py +31 -16
  46. py2docfx/venv/venv1/Lib/site-packages/jwt/api_jws.py +19 -8
  47. py2docfx/venv/venv1/Lib/site-packages/jwt/api_jwt.py +75 -19
  48. py2docfx/venv/venv1/Lib/site-packages/jwt/exceptions.py +8 -0
  49. py2docfx/venv/venv1/Lib/site-packages/jwt/help.py +4 -1
  50. py2docfx/venv/venv1/Lib/site-packages/jwt/jwks_client.py +4 -2
  51. py2docfx/venv/venv1/Lib/site-packages/jwt/utils.py +7 -10
  52. py2docfx/venv/venv1/Lib/site-packages/msal/application.py +1 -1
  53. py2docfx/venv/venv1/Lib/site-packages/msal/managed_identity.py +5 -3
  54. py2docfx/venv/venv1/Lib/site-packages/setuptools/build_meta.py +2 -2
  55. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/bdist_egg.py +1 -1
  56. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/bdist_wheel.py +25 -39
  57. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/build_ext.py +2 -2
  58. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/build_py.py +9 -14
  59. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/easy_install.py +2 -2
  60. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/editable_wheel.py +2 -2
  61. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/egg_info.py +3 -2
  62. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/install_egg_info.py +2 -2
  63. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/saveopts.py +2 -2
  64. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/sdist.py +2 -2
  65. py2docfx/venv/venv1/Lib/site-packages/setuptools/command/setopt.py +1 -1
  66. py2docfx/venv/venv1/Lib/site-packages/setuptools/config/pyprojecttoml.py +0 -13
  67. py2docfx/venv/venv1/Lib/site-packages/setuptools/dist.py +3 -2
  68. py2docfx/venv/venv1/Lib/site-packages/setuptools/monkey.py +3 -3
  69. py2docfx/venv/venv1/Lib/site-packages/setuptools/msvc.py +11 -11
  70. py2docfx/venv/venv1/Lib/site-packages/setuptools/tests/config/test_pyprojecttoml.py +0 -7
  71. py2docfx/venv/venv1/Lib/site-packages/setuptools/tests/test_core_metadata.py +168 -72
  72. py2docfx/venv/venv1/Lib/site-packages/setuptools/unicode_utils.py +3 -3
  73. py2docfx/venv/venv1/Lib/site-packages/wheel/__init__.py +1 -1
  74. py2docfx/venv/venv1/Lib/site-packages/wheel/cli/convert.py +1 -2
  75. {py2docfx-0.1.9.dev1917798.dist-info → py2docfx-0.1.9.dev1926139.dist-info}/METADATA +1 -1
  76. {py2docfx-0.1.9.dev1917798.dist-info → py2docfx-0.1.9.dev1926139.dist-info}/RECORD +79 -77
  77. {py2docfx-0.1.9.dev1917798.dist-info → py2docfx-0.1.9.dev1926139.dist-info}/WHEEL +1 -1
  78. /py2docfx/convert_prepare/conf_templates/{master_doc.rst_t → root_doc.rst_t} +0 -0
  79. {py2docfx-0.1.9.dev1917798.dist-info → py2docfx-0.1.9.dev1926139.dist-info}/top_level.txt +0 -0
py2docfx/__main__.py CHANGED
@@ -1,11 +1,13 @@
1
1
  from __future__ import annotations # Avoid A | B annotation break under <= py3.9
2
2
  import asyncio
3
3
  import argparse
4
+ import logging
4
5
  import os
5
6
  import sys
6
7
  import shutil
7
8
 
8
9
  from py2docfx import PACKAGE_ROOT
10
+ from py2docfx.docfx_yaml.logger import get_logger
9
11
  from py2docfx.convert_prepare.constants import SOURCE_REPO, TARGET_REPO, DIST_TEMP
10
12
  from py2docfx.convert_prepare.generate_document import generate_document
11
13
  from py2docfx.convert_prepare.get_source import YAML_OUTPUT_ROOT
@@ -14,11 +16,6 @@ from py2docfx.convert_prepare.params import load_file_params, load_command_param
14
16
  from py2docfx.convert_prepare.package_info import PackageInfo
15
17
  import py2docfx.convert_prepare.environment as py2docfxEnvironment
16
18
 
17
-
18
- print("Adding yaml extension to path")
19
- sys.path.insert(0, os.path.join(os.path.dirname(os.path.abspath(__file__)),'docfx_yaml'))
20
- os.chdir(PACKAGE_ROOT)
21
-
22
19
  def get_parser() -> argparse.ArgumentParser:
23
20
  parser = argparse.ArgumentParser(
24
21
  description=(
@@ -144,26 +141,40 @@ def get_parser() -> argparse.ArgumentParser:
144
141
  help="""A list containing relative paths to the root of the package of files/directories
145
142
  excluded when generating documents, should follow fnmatch-style.""",
146
143
  )
144
+
145
+ parser.add_argument(
146
+ "--verbose",
147
+ action="store_true",
148
+ help="""Increase output verbosity. Cannot be used together with --show-warning""",
149
+ )
150
+
151
+ parser.add_argument(
152
+ "--show-warning",
153
+ action="store_true",
154
+ help="""Show warning message. Cannot be used together with --verbose""",
155
+ )
147
156
  return parser
148
157
 
149
158
 
150
159
  def parse_command_line_args(argv) -> (
151
- list[PackageInfo], list[PackageInfo], str, str, str | os.PathLike, bool):
160
+ list[PackageInfo], list[PackageInfo], str, str, str | os.PathLike, bool, bool):
152
161
  parser = get_parser()
153
162
  args = parser.parse_args(argv)
154
163
 
155
164
  github_token = args.github_token
156
165
  ado_token = args.ado_token
157
166
  output_root = args.output_root
167
+ verbose = args.verbose
168
+ show_warning = args.show_warning
158
169
 
159
170
  if args.param_file_path:
160
171
  (package_info_list, required_packages) = load_file_params(args.param_file_path)
161
172
  return (list(package_info_list), list(required_packages), github_token,
162
- ado_token, output_root)
173
+ ado_token, output_root, verbose, show_warning)
163
174
  elif args.param_json:
164
175
  (package_info_list, required_packages) = load_command_params(args.param_json)
165
176
  return (package_info_list, required_packages, github_token,
166
- ado_token, output_root)
177
+ ado_token, output_root, verbose, show_warning)
167
178
  else:
168
179
  package_info = PackageInfo()
169
180
  if not args.install_type:
@@ -194,11 +205,11 @@ def parse_command_line_args(argv) -> (
194
205
  package_info.folder = args.folder
195
206
  if not package_info.url:
196
207
  if not package_info.folder:
197
- raise ValueError(
198
- "When install_type is source_code, folder or url should be provided"
199
- )
208
+ msg = "When install_type is source_code, folder or url should be provided"
209
+ raise ValueError(msg)
200
210
  else:
201
- print(f'Read source code from local folder: {package_info.folder}')
211
+ msg = f"Read source code from local folder: {package_info.folder}"
212
+ logging.info(msg)
202
213
 
203
214
  if package_info.install_type == PackageInfo.InstallType.DIST_FILE:
204
215
  package_info.location = args.location
@@ -208,7 +219,7 @@ def parse_command_line_args(argv) -> (
208
219
  "None",
209
220
  condition="When install_type is dist_file",
210
221
  )
211
- return ([package_info], [], github_token, ado_token, output_root)
222
+ return ([package_info], [], github_token, ado_token, output_root, verbose, show_warning)
212
223
 
213
224
  async def donwload_package_generate_documents(
214
225
  package_info_list: list[PackageInfo],
@@ -216,6 +227,8 @@ async def donwload_package_generate_documents(
216
227
  output_doc_folder: os.PathLike | None,
217
228
  github_token: str, ado_token: str, required_package_list: list):
218
229
 
230
+ docfx_logger = get_logger(__name__)
231
+
219
232
  start_num = len(required_package_list)
220
233
  env_prepare_tasks = []
221
234
  env_remove_tasks = []
@@ -229,12 +242,16 @@ async def donwload_package_generate_documents(
229
242
  py2docfxEnvironment.prepare_base_venv(required_package_list, github_token, ado_token))
230
243
 
231
244
  for idx, package in enumerate(package_info_list):
245
+ os.environ['PROCESSING_PACKAGE_NAME'] = package.name
232
246
  package_number = start_num + idx
233
- print(f"Processing package {package.name}, env_prepare_tasks: {len(env_prepare_tasks)}")
247
+ msg = f"Processing package {package.name}, env_prepare_tasks: {len(env_prepare_tasks)}"
248
+ docfx_logger.info(msg)
249
+
234
250
  try:
235
251
  await env_prepare_tasks[idx]
236
252
  except Exception as e:
237
- print(f"Failed to setup venv for package {package.name}: {e}")
253
+ msg = f"Failed to setup venv for package {package.name}: {e}"
254
+ docfx_logger.error(msg)
238
255
  raise
239
256
 
240
257
  generate_document(package, output_root,
@@ -249,7 +266,10 @@ async def donwload_package_generate_documents(
249
266
 
250
267
  if idx + py2docfxEnvironment.VENV_BUFFER < len(package_info_list):
251
268
  buffer_package_idx = idx + py2docfxEnvironment.VENV_BUFFER
252
- print(f"Creating venv {buffer_package_idx}")
269
+
270
+ msg = f"Creating venv {buffer_package_idx}"
271
+ docfx_logger.info(msg)
272
+
253
273
  env_prepare_tasks.append(
254
274
  asyncio.create_task(py2docfxEnvironment.prepare_venv(buffer_package_idx,
255
275
  package_info_list[buffer_package_idx],
@@ -262,7 +282,8 @@ async def donwload_package_generate_documents(
262
282
  py2docfxEnvironment.remove_environment(idx-1)))
263
283
 
264
284
  if idx > py2docfxEnvironment.VENV_BUFFER and env_remove_tasks[idx-py2docfxEnvironment.VENV_BUFFER] != None:
265
- print(f"Removing venv {idx-py2docfxEnvironment.VENV_BUFFER}")
285
+ msg = f"Removing venv {idx-py2docfxEnvironment.VENV_BUFFER}"
286
+ docfx_logger.info(msg)
266
287
  await env_remove_tasks[idx-py2docfxEnvironment.VENV_BUFFER]
267
288
 
268
289
  if output_doc_folder:
@@ -295,24 +316,58 @@ def temp_folder_clean_up(folder_list: list[str | os.PathLike]) -> None:
295
316
  if os.path.exists(folder):
296
317
  shutil.rmtree(folder)
297
318
 
298
- def main(argv) -> int:
299
- clean_up_folder_list = [py2docfxEnvironment.VENV_DIR, DIST_TEMP, SOURCE_REPO, TARGET_REPO]
300
- temp_folder_clean_up(clean_up_folder_list)
319
+ def decide_global_log_level(verbose: bool, show_warning: bool) -> None:
320
+ if verbose and show_warning:
321
+ raise ValueError("Cannot use --verbose and --show-warning at the same time")
322
+ if verbose:
323
+ os.environ['LOG_LEVEL'] = 'INFO'
324
+ return
325
+ if show_warning:
326
+ os.environ['LOG_LEVEL'] = 'WARNING'
327
+ return
328
+
329
+ # Default log level
330
+ os.environ['LOG_LEVEL'] = 'ERROR'
301
331
 
332
+ def prepare_log_folder() -> None:
333
+ if not os.path.exists('logs'):
334
+ os.makedirs('logs')
335
+ os.makedirs(os.path.join('logs', 'package_logs'))
336
+ else:
337
+ shutil.rmtree('logs')
338
+ os.makedirs('logs')
339
+ os.makedirs(os.path.join('logs', 'package_logs'))
340
+
341
+ def main(argv) -> int:
302
342
  # TODO: may need to purge pip cache
303
343
  (package_info_list,
304
344
  required_package_list,
305
345
  github_token, ado_token,
306
- output_root) = parse_command_line_args(argv)
346
+ output_root, verbose,
347
+ show_warning) = parse_command_line_args(argv)
307
348
 
349
+ decide_global_log_level(verbose, show_warning)
350
+ prepare_log_folder()
351
+
352
+ docfx_logger = get_logger(__name__)
353
+
354
+ msg = "Adding yaml extension to path"
355
+ docfx_logger.info(msg)
356
+
357
+ sys.path.insert(0, os.path.join(os.path.dirname(os.path.abspath(__file__)),'docfx_yaml'))
358
+ os.chdir(PACKAGE_ROOT)
308
359
  output_doc_folder = prepare_out_dir(output_root)
360
+
361
+ clean_up_folder_list = [py2docfxEnvironment.VENV_DIR, DIST_TEMP, SOURCE_REPO, TARGET_REPO]
362
+ temp_folder_clean_up(clean_up_folder_list)
309
363
 
310
364
  try:
311
365
  asyncio.run(donwload_package_generate_documents(
312
366
  package_info_list, output_root, output_doc_folder,
313
367
  github_token, ado_token, required_package_list))
314
368
  except Exception as e:
315
- print(f"An error occurred: {e}")
369
+ msg = f"An error occurred: {e}"
370
+ docfx_logger.error(msg)
316
371
  raise
317
372
  return 0
318
373
 
@@ -6,6 +6,7 @@ from py2docfx import PACKAGE_ROOT
6
6
  from py2docfx.convert_prepare.package_info import PackageInfo
7
7
  from py2docfx.convert_prepare.get_source import get_source
8
8
  from py2docfx.convert_prepare import pip_utils
9
+ from py2docfx.docfx_yaml.logger import get_logger
9
10
 
10
11
  REQUIREMENT_MODULES = ["setuptools", "sphinx==6.1.3", "pyyaml", "jinja2==3.0.3", "wheel"]
11
12
  VENV_REQUIREMENT_MODULES = ["setuptools", "wheel"] # to support running setup.py in venv
@@ -27,7 +28,7 @@ def install_converter_requirements(executable: str):
27
28
  https://apidrop.visualstudio.com/Content%20CI/_git/ReferenceAutomation?path=/Python/InstallPackage.ps1&line=15&lineEnd=35&lineStartColumn=1&lineEndColumn=87&lineStyle=plain&_a=contents
28
29
  """
29
30
  pip_install_cmd = [executable, "-m", "pip", "install", "--upgrade"]
30
-
31
+ docfx_logger = get_logger(__name__)
31
32
  pip_install_common_options = [
32
33
  "--no-cache-dir",
33
34
  "--quiet",
@@ -37,7 +38,8 @@ def install_converter_requirements(executable: str):
37
38
  ]
38
39
 
39
40
  for module in REQUIREMENT_MODULES:
40
- print(f"<CI INFO>: Upgrading {module}...")
41
+ msg = f"<CI INFO>: Upgrading {module}..."
42
+ docfx_logger.info(msg)
41
43
  subprocess.run(
42
44
  pip_install_cmd + [module] + pip_install_common_options, check=True
43
45
  )
@@ -45,7 +47,8 @@ def install_converter_requirements(executable: str):
45
47
  async def install_venv_requirements(venv_num: int):
46
48
  venv_exe = get_venv_exe(venv_num)
47
49
  pip_cmd = ["-m", "pip", "install", "--upgrade"]+ VENV_REQUIREMENT_MODULES
48
- await(await asyncio.create_subprocess_exec(venv_exe, *pip_cmd)).wait()
50
+ # await(await asyncio.create_subprocess_exec(venv_exe, *pip_cmd)).wait()
51
+ await pip_utils.run_async_subprocess(venv_exe, pip_cmd)
49
52
 
50
53
  def get_venv_path(venv_num: int) -> str:
51
54
  return os.path.join(PACKAGE_ROOT, VENV_DIR, "venv"+str(venv_num))
@@ -82,7 +85,8 @@ def get_base_venv_sphinx_build_path() -> str:
82
85
 
83
86
  async def install_converter_requirement_async(executable: str):
84
87
  pip_cmd = PIP_INSTALL_COMMAND + PIP_INSTALL_VENV_COMMON_OPTIONS + REQUIREMENT_MODULES
85
- await(await asyncio.create_subprocess_exec(executable, *pip_cmd)).wait()
88
+ # await(await asyncio.create_subprocess_exec(executable, *pip_cmd)).wait()
89
+ await pip_utils.run_async_subprocess(executable, pip_cmd)
86
90
 
87
91
  async def install_required_packages(
88
92
  executable: str, required_package_list: list[PackageInfo], github_token: str, ado_token: str):
@@ -92,7 +96,8 @@ async def install_required_packages(
92
96
  # get_source(package, idx, vststoken=ado_token, githubtoken=github_token)
93
97
  package_name, options = package.get_install_command()
94
98
  pip_cmd = PIP_INSTALL_COMMAND + PIP_INSTALL_VENV_COMMON_OPTIONS + options + [package_name]
95
- await(await asyncio.create_subprocess_exec(executable, *pip_cmd)).wait()
99
+ # await(await asyncio.create_subprocess_exec(executable, *pip_cmd)).wait()
100
+ await pip_utils.run_async_subprocess(executable, pip_cmd)
96
101
 
97
102
  async def create_environment(venv_path: int):
98
103
  if os.name == 'nt':
@@ -101,26 +106,39 @@ async def create_environment(venv_path: int):
101
106
  await (await asyncio.create_subprocess_exec("python3", "-m", "venv", venv_path)).wait()
102
107
 
103
108
  async def prepare_base_venv(required_package_list: list[PackageInfo], github_token: str, ado_token: str):
104
- print(f"<CI INFO>: Creating basevenv...")
109
+ docfx_logger = get_logger(__name__)
110
+
111
+ msg = f"<CI INFO>: Creating basevenv..."
112
+ docfx_logger.info(msg)
105
113
  await create_environment(get_base_venv_path())
106
- print(f"<CI INFO>: Installing converter requirements in ...")
114
+
115
+ msg = f"<CI INFO>: Installing converter requirements in ..."
116
+ docfx_logger.info(msg)
107
117
  await install_converter_requirement_async(get_base_venv_exe())
108
- print(f"<CI INFO>: Installing required packages in basevenv...")
118
+
119
+ msg = f"<CI INFO>: Installing required packages in basevenv..."
120
+ docfx_logger.info(msg)
109
121
  await install_required_packages(get_base_venv_exe(), required_package_list, github_token, ado_token)
110
- print(f"<CI INFO>: basevenv setup complete.")
122
+
123
+ msg = f"<CI INFO>: basevenv setup complete."
124
+ docfx_logger.info(msg)
111
125
 
112
126
  async def prepare_venv(venv_num: int, package_info: PackageInfo, package_number: int, github_token: str, ado_token: str):
127
+ docfx_logger = get_logger(__name__)
113
128
  await create_environment(get_venv_path(venv_num))
114
129
  await install_venv_requirements(venv_num)
115
130
  get_source(get_venv_exe(venv_num), package_info, package_number, vststoken=ado_token, githubtoken=github_token)
116
131
  package_name, options = package_info.get_install_command()
117
132
  await pip_utils.install_in_exe_async(get_venv_exe(venv_num), package_name, options)
118
- print(f"<CI INFO>: venv{venv_num} setup complete.")
133
+ msg = f"<CI INFO>: venv{venv_num} setup complete."
134
+ docfx_logger.info(msg)
119
135
 
120
136
  async def remove_environment(venv_num: int):
137
+ docfx_logger = get_logger(__name__)
121
138
  venv_path = get_venv_path(venv_num)
122
139
  if os.path.exists(venv_path):
123
- print(f"<CI INFO>: Removing venv{venv_num}...")
140
+ msg = f"<CI INFO>: Removing venv{venv_num}..."
141
+ docfx_logger.info(msg)
124
142
  # Create a subprocess to run the shell command for removing the directory
125
143
  process = await asyncio.create_subprocess_shell(
126
144
  f'rm -rf {venv_path}' if os.name != 'nt' else f'rmdir /S /Q {venv_path}',
@@ -129,6 +147,9 @@ async def remove_environment(venv_num: int):
129
147
  )
130
148
  stdout, stderr = await process.communicate()
131
149
  if process.returncode == 0:
132
- print(f"<CI INFO>: venv{venv_num} removed.")
150
+ msg = f"<CI INFO>: venv{venv_num} removed."
151
+ docfx_logger.info(msg)
133
152
  else:
134
- print(f"<CI ERROR>: Failed to remove venv{venv_num}. Error: {stderr.decode()}")
153
+ msg = f"<CI ERROR>: Failed to remove venv{venv_num}. Error: {stderr.decode()}"
154
+ docfx_logger.error(msg)
155
+ raise RuntimeError()
@@ -1,7 +1,7 @@
1
1
  from __future__ import annotations # Avoid A | B annotation break under <= py3.9
2
2
  import os
3
3
  import sys
4
-
4
+ from py2docfx.docfx_yaml.logger import get_logger
5
5
  from py2docfx.convert_prepare.generate_conf import generate_conf
6
6
  from py2docfx.convert_prepare.git import checkout
7
7
  from py2docfx.convert_prepare.package_info import PackageInfo
@@ -11,6 +11,7 @@ from py2docfx.convert_prepare.subpackage import merge_subpackage_files
11
11
  CONF_TEMPLATE_DIR = os.path.join(os.path.dirname(os.path.realpath(__file__)), "conf_templates")
12
12
 
13
13
  def generate_document(pkg: PackageInfo, output_root: str | os.PathLike, sphinx_build_path: str, extra_package_path: str, executable=sys.executable):
14
+ docfx_logger = get_logger(__name__)
14
15
  # Copy manual written RST from target doc repo
15
16
  package_paths = pkg.path
16
17
  if output_root:
@@ -29,14 +30,20 @@ def generate_document(pkg: PackageInfo, output_root: str | os.PathLike, sphinx_b
29
30
  if pkg.install_type == pkg.InstallType.SOURCE_CODE and getattr(pkg, "branch", None):
30
31
  checkout(package_paths.source_folder, pkg.branch)
31
32
 
32
- print(f"<CI INFO>: Generating RST files for {pkg.name}.")
33
+ msg = f"<CI INFO>: Generating RST files for {pkg.name}."
34
+ docfx_logger.info(msg)
35
+
33
36
  subpackages_rst_record = run_apidoc(package_paths.doc_folder, package_paths.source_folder,
34
37
  exclude_paths, pkg)
35
38
 
36
- print("<CI INFO>: Listing RST files:")
39
+ msg = f"<CI INFO>: Listing RST files:"
40
+ docfx_logger.info(msg)
37
41
  for rst_file in os.listdir(package_paths.doc_folder):
38
- print(rst_file)
39
- print("<CI INFO>: Running Sphinx build...")
42
+ docfx_logger.info(rst_file)
43
+
44
+ msg = "<CI INFO>: Running Sphinx build..."
45
+ docfx_logger.info(msg)
46
+
40
47
  generate_conf(pkg, package_paths.doc_folder, CONF_TEMPLATE_DIR)
41
48
  run_converter(package_paths.doc_folder, package_paths.yaml_output_folder, sphinx_build_path, extra_package_path, executable=executable)
42
49
 
@@ -6,6 +6,7 @@ import sys
6
6
  import py2docfx.convert_prepare.git as git
7
7
  import py2docfx.convert_prepare.pip_utils as pip_utils
8
8
  import py2docfx.convert_prepare.pack as pack
9
+ from py2docfx.docfx_yaml.logger import get_logger
9
10
  from py2docfx.convert_prepare.constants import TARGET_REPO, SOURCE_REPO, DIST_TEMP
10
11
  from py2docfx.convert_prepare.package_info import PackageInfo
11
12
  from py2docfx.convert_prepare.source import Source
@@ -72,6 +73,7 @@ def update_package_info(executable: str, pkg: PackageInfo, source_folder: str):
72
73
  )
73
74
 
74
75
  def get_source(executable: str, pkg: PackageInfo, cnt: int, vststoken=None, githubtoken=None):
76
+ docfx_logger = get_logger(__name__)
75
77
  path_cnt = str(cnt)
76
78
  dist_dir = path.join(DIST_TEMP, path_cnt)
77
79
 
@@ -120,6 +122,8 @@ def get_source(executable: str, pkg: PackageInfo, cnt: int, vststoken=None, gith
120
122
  os.listdir(dist_dir)[0]
121
123
  )
122
124
  else:
123
- raise ValueError(f"Unknown install type: {pkg.install_type}")
125
+ msg = f"Unknown install type: {pkg.install_type}"
126
+ docfx_logger.error(msg)
127
+ raise ValueError()
124
128
 
125
129
  update_package_info(executable, pkg, source_folder)
@@ -1,8 +1,9 @@
1
1
  import re
2
2
  import subprocess
3
3
 
4
- repoMap = {}
4
+ from py2docfx.docfx_yaml.logger import get_logger
5
5
 
6
+ repoMap = {}
6
7
 
7
8
  def clone(repo_location, branch, folder, extra_token=None):
8
9
  """
@@ -12,15 +13,16 @@ def clone(repo_location, branch, folder, extra_token=None):
12
13
  replacing
13
14
  https://apidrop.visualstudio.com/Content%20CI/_git/ReferenceAutomation?path=/Python/GetPackageCode.ps1&line=50&lineEnd=90&lineStartColumn=1&lineEndColumn=2&lineStyle=plain&_a=contents
14
15
  """
15
-
16
- print("<CI INFO>: Cloning repo: {}...".format(repo_location))
16
+ docfx_logger = get_logger(__name__)
17
+ msg = "<CI INFO>: Cloning repo: {}...".format(repo_location)
18
+ docfx_logger.info(msg)
17
19
 
18
20
  global repoMap
19
21
 
20
22
  if not test_url(repo_location, extra_token):
21
- raise ValueError(
22
- "Git repo address {} is not a valid URL.".format(repo_location)
23
- )
23
+ msg = "Git repo address {} is not a valid URL.".format(repo_location)
24
+ docfx_logger.error(msg)
25
+ raise ValueError()
24
26
  else:
25
27
  # Remove http(s):// from url to record. Further avoid dup-clone.
26
28
  pureURL = re.sub("^\s*https?://", "", repo_location)
@@ -57,17 +59,17 @@ def clone(repo_location, branch, folder, extra_token=None):
57
59
  ]
58
60
  subprocess.run(clone_params, check=True)
59
61
  repoMap[pureURL] = folder
60
- print(
61
- "<CI INFO>: Repo {} successfully cloned in {}...".format(
62
+ msg = "<CI INFO>: Repo {} successfully cloned in {}...".format(
62
63
  repo_location, repoMap[pureURL]
63
64
  )
64
- )
65
+ docfx_logger.info(msg)
65
66
  else:
66
67
  raise ValueError(
67
68
  "Branch {} doesn't exist in repo {}.".format(branch, repo_location)
68
69
  )
69
70
  else:
70
- print("<CI INFO>: Repo already cloned in {}...".format(repoMap[pureURL]))
71
+ msg = "<CI INFO>: Repo already cloned in {}...".format(repoMap[pureURL])
72
+ docfx_logger.info(msg)
71
73
 
72
74
  return repoMap[pureURL]
73
75
 
@@ -76,9 +78,12 @@ def test_url(url, extraHeader):
76
78
  """
77
79
  Test if the url is a valid git repo url
78
80
  """
81
+ docfx_logger = get_logger(__name__)
79
82
  params = ["git", "ls-remote", url]
80
83
  if extraHeader:
81
- print("Using extra header to test git repo url.")
84
+ msg = "Using extra header to test git repo url."
85
+ docfx_logger.info(msg)
86
+
82
87
  params[1:1] = [
83
88
  "-c",
84
89
  "http.extraHeader=Authorization: Basic {}".format(extraHeader),
@@ -91,13 +96,13 @@ def test_url(url, extraHeader):
91
96
 
92
97
 
93
98
  def convertBranch(repo_url, branch, extraHeader):
99
+ docfx_logger = get_logger(__name__)
94
100
  result = branch
95
101
  if not branch:
96
- print(
97
- "Using empty branch of {}, going to use master branch instead.".format(
102
+ msg = "Using empty branch of {}, going to use master branch instead.".format(
98
103
  repo_url
99
104
  )
100
- )
105
+ docfx_logger.info(msg)
101
106
  result = "master"
102
107
  if result == "master":
103
108
  check_params = ["git", "ls-remote", "--heads", repo_url, "refs/heads/main"]
@@ -109,11 +114,10 @@ def convertBranch(repo_url, branch, extraHeader):
109
114
 
110
115
  checkBr = subprocess.check_output(check_params)
111
116
  if checkBr:
112
- print(
113
- "Using master branch of {}, going to use main branch instead.".format(
117
+ msg = "Using master branch of {}, going to use main branch instead.".format(
114
118
  repo_url
115
119
  )
116
- )
120
+ docfx_logger.info(msg)
117
121
  result = "main"
118
122
  return result
119
123
 
@@ -125,7 +129,7 @@ def checkout(folder, branch):
125
129
  Replacing
126
130
  https://apidrop.visualstudio.com/Content%20CI/_git/ReferenceAutomation?path=/Python/PyCommon.ps1&line=707&lineEnd=763&lineStartColumn=1&lineEndColumn=2&lineStyle=plain&_a=contents
127
131
  """
128
-
132
+ docfx_logger = get_logger(__name__)
129
133
  remote = "origin"
130
134
 
131
135
  if ":" in branch:
@@ -153,8 +157,8 @@ def checkout(folder, branch):
153
157
  )
154
158
 
155
159
  subprocess.run(["git", "-C", folder, "checkout", "--quiet", branch])
156
-
157
- print("<CI INFO>: Switched to branch {}.".format(branch))
160
+ msg = "<CI INFO>: Switched to branch {}.".format(branch)
161
+ docfx_logger.info(msg)
158
162
 
159
163
 
160
164
  def commit_and_push(repo_location, folder, extra_token=None):
@@ -1,6 +1,7 @@
1
1
  from enum import Enum
2
2
  import os
3
3
  import re
4
+ from py2docfx.docfx_yaml.logger import get_logger
4
5
  from py2docfx.convert_prepare.source import Source
5
6
  from py2docfx.convert_prepare.package_info_extra_settings import extra_exclude_path_by_package
6
7
 
@@ -9,14 +10,13 @@ class PackageInfo:
9
10
  PYPI = 1
10
11
  SOURCE_CODE = 2
11
12
  DIST_FILE = 3
12
-
13
13
  path: Source
14
-
15
14
  def __init__(self) -> None:
16
15
  pass
17
-
16
+
18
17
  @classmethod
19
18
  def report_error(cls, name, value, condition=None):
19
+ docfx_logger = get_logger(__name__)
20
20
  if condition:
21
21
  message = "When {0}, found unexpected property of {1}, loaded value is: {2}".format(
22
22
  condition, name, value
@@ -25,7 +25,8 @@ class PackageInfo:
25
25
  message = "Found unexpected property of {0}, loaded value is: {1}".format(
26
26
  name, value
27
27
  )
28
- raise ValueError(message)
28
+ docfx_logger.error(message)
29
+ raise ValueError()
29
30
 
30
31
  @classmethod
31
32
  def parse_from(cls, dict, reading_required_packages=False):
@@ -59,12 +60,14 @@ class PackageInfo:
59
60
  package_info.folder = package_info_dict.get("folder", None)
60
61
 
61
62
  if not package_info.url:
63
+ docfx_logger = get_logger(__name__)
62
64
  if not package_info.folder:
63
- raise ValueError(
64
- "When install_type is source_code, folder or url should be provided"
65
- )
65
+ msg = "When install_type is source_code, url or folder should be provided"
66
+ docfx_logger.error(msg)
67
+ raise ValueError()
66
68
  else:
67
- print(f'Read source code from local folder: {package_info.folder}')
69
+ msg = f'Read source code from local folder: {package_info.folder}'
70
+ docfx_logger.info(msg)
68
71
 
69
72
  prefer_source_distribution = package_info_dict.get(
70
73
  "prefer_source_distribution", False
@@ -140,10 +143,13 @@ class PackageInfo:
140
143
  return (packageInstallName, pipInstallExtraOptions)
141
144
 
142
145
  def get_exluded_command(self) -> []:
146
+ docfx_logger = get_logger(__name__)
143
147
  if hasattr(self, "path"):
144
148
  code_location = self.path.source_folder
145
149
  else:
146
- raise ValueError("Should set source code location before build documents")
150
+ msg = "Should set source code location before build documents"
151
+ docfx_logger.error(msg)
152
+ raise ValueError()
147
153
  exclude_path = []
148
154
  if code_location:
149
155
  exclude_path.append(os.path.join(code_location, "build/*"))
@@ -1,6 +1,8 @@
1
1
  import subprocess
2
2
  import asyncio
3
+ import os
3
4
  from py2docfx import PACKAGE_ROOT
5
+ from py2docfx.docfx_yaml.logger import get_logger, log_subprocess_ouput
4
6
 
5
7
  PYPI = "pypi"
6
8
 
@@ -10,10 +12,9 @@ pip_install_common_options = [
10
12
  "--no-compile",
11
13
  "--no-warn-conflicts",
12
14
  "--disable-pip-version-check",
13
- "--verbose",
15
+ "--verbose"
14
16
  ]
15
17
 
16
-
17
18
  def download(package_name, path, extra_index_url=None, prefer_source_distribution=True):
18
19
  # Downloads a package from PyPI to the specified path using pip.
19
20
  download_param = ["pip", "download", "--dest", path, "--no-deps", package_name]
@@ -24,7 +25,9 @@ def download(package_name, path, extra_index_url=None, prefer_source_distributio
24
25
  download_param.append("--no-binary=:all:")
25
26
  else:
26
27
  download_param.append("--prefer-binary")
27
- subprocess.run(download_param, check=True, cwd=PACKAGE_ROOT)
28
+ output = subprocess.run(download_param, check=True, cwd=PACKAGE_ROOT, capture_output=True, text=True)
29
+ docfx_logger = get_logger(__name__)
30
+ log_subprocess_ouput(output, docfx_logger)
28
31
 
29
32
 
30
33
  def install(package_name, options):
@@ -32,16 +35,34 @@ def install(package_name, options):
32
35
  install_param = "pip install {} {}".format(
33
36
  " ".join(pip_install_common_options + options), package_name
34
37
  ).split(" ")
35
- subprocess.run(install_param, check=True, cwd=PACKAGE_ROOT)
36
-
38
+ output = subprocess.run(install_param, check=True, cwd=PACKAGE_ROOT, capture_output=True, text=True)
39
+ docfx_logger = get_logger(__name__)
40
+ log_subprocess_ouput(output, docfx_logger)
37
41
 
38
42
  def install_in_exe(exe_path, package_name, options):
39
43
  # Installs a package from PyPI using pip.
40
44
  install_param = [exe_path] + "-m pip install {} {}".format(
41
45
  " ".join(pip_install_common_options + options), package_name
42
46
  ).split(" ")
43
- subprocess.run(install_param, check=True, cwd=PACKAGE_ROOT)
44
-
47
+ output = subprocess.run(install_param, check=True, cwd=PACKAGE_ROOT, capture_output=True, text=True)
48
+ docfx_logger = get_logger(__name__)
49
+ log_subprocess_ouput(output, docfx_logger)
50
+
45
51
  async def install_in_exe_async(exe_path, package_name, options):
46
52
  pip_cmd = ["-m", "pip", "install"]+ pip_install_common_options + options + [package_name]
47
- await(await asyncio.create_subprocess_exec(exe_path, *pip_cmd)).wait()
53
+ await run_async_subprocess(exe_path, pip_cmd)
54
+ # await(await asyncio.create_subprocess_exec(exe_path, *pip_cmd)).wait()
55
+
56
+ async def run_async_subprocess(exe_path, cmd):
57
+ process = await asyncio.create_subprocess_exec(
58
+ exe_path, *cmd,
59
+ stdout=asyncio.subprocess.PIPE,
60
+ stderr=asyncio.subprocess.PIPE
61
+ )
62
+ stdout, stderr = await process.communicate()
63
+ docfx_logger = get_logger(__name__)
64
+ if process.returncode != 0:
65
+ docfx_logger.error(stderr.decode('utf-8'))
66
+ raise RuntimeError()
67
+ else:
68
+ docfx_logger.info(stdout.decode('utf-8'))
@@ -2,10 +2,13 @@ from __future__ import annotations # Avoid A | B annotation break under <= py3.9
2
2
  import os
3
3
  import shutil
4
4
 
5
+ from py2docfx.docfx_yaml.logger import get_logger
6
+
5
7
  TOC_FILE_PATH = "toc.yml"
6
8
  PACKAGE_TOC_FILE_PATH = "_build/docfx_yaml/toc.yml"
7
9
  def merge_toc(
8
10
  root_doc_path: str | os.PathLike, package_doc_path: str | os.PathLike):
11
+ docfx_logger = get_logger(__name__)
9
12
  root_toc_path = os.path.join(root_doc_path, TOC_FILE_PATH)
10
13
  package_toc_path = os.path.join(package_doc_path, PACKAGE_TOC_FILE_PATH)
11
14
 
@@ -18,7 +21,8 @@ def merge_toc(
18
21
  if not toc_content.endswith("\n"):
19
22
  root_toc_handle.write("\n")
20
23
  else:
21
- raise ValueError(f"TOC content empty: {package_toc_path}")
24
+ docfx_logger.error(f"TOC content empty: {package_toc_path}")
25
+ raise ValueError()
22
26
 
23
27
  # delete package toc.yml
24
28
  os.remove(package_toc_path)