python-package-folder 4.1.0__tar.gz → 4.1.1__tar.gz

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 (52) hide show
  1. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/PKG-INFO +1 -1
  2. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/coverage.svg +2 -2
  3. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/pyproject.toml +1 -1
  4. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/python_package_folder.py +129 -31
  5. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/.copier-answers.yml +0 -0
  6. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/.cursor/plans/optional_version_+_semantic-release_efed88a6.plan.md +0 -0
  7. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/.cursor/rules/general.mdc +0 -0
  8. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/.cursor/rules/python.mdc +0 -0
  9. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/.github/workflows/ci.yml +0 -0
  10. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/.github/workflows/publish.yml +0 -0
  11. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/.gitignore +0 -0
  12. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/.vscode/settings.json +0 -0
  13. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/LICENSE +0 -0
  14. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/Makefile +0 -0
  15. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/README.md +0 -0
  16. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/development.md +0 -0
  17. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/installation.md +0 -0
  18. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/publishing.md +0 -0
  19. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/python_package_folder/scripts/get-next-version.cjs +0 -0
  20. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/scripts/get-next-version.cjs +0 -0
  21. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/__init__.py +0 -0
  22. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/__main__.py +0 -0
  23. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/_hatch_build.py +0 -0
  24. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/analyzer.py +0 -0
  25. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/finder.py +0 -0
  26. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/manager.py +0 -0
  27. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/publisher.py +0 -0
  28. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/py.typed +0 -0
  29. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/subfolder_build.py +0 -0
  30. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/types.py +0 -0
  31. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/utils.py +0 -0
  32. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/src/python_package_folder/version.py +0 -0
  33. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/conftest.py +0 -0
  34. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/folder_structure/some_globals.py +0 -0
  35. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/folder_structure/subfolder_to_build/README.md +0 -0
  36. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/folder_structure/subfolder_to_build/__init__.py +0 -0
  37. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/folder_structure/subfolder_to_build/some_function.py +0 -0
  38. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/folder_structure/subfolder_to_build/some_globals.py +0 -0
  39. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/folder_structure/utility_folder/_SS/some_superseded_file.py +0 -0
  40. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/folder_structure/utility_folder/some_utility.py +0 -0
  41. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_build_with_external_deps.py +0 -0
  42. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_linting.py +0 -0
  43. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_preserve_directory_structure.py +0 -0
  44. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_publisher.py +0 -0
  45. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_shared_subdirectory_imports.py +0 -0
  46. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_spreadsheet_creation_imports.py +0 -0
  47. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_subfolder_build.py +0 -0
  48. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_third_party_dependencies.py +0 -0
  49. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_utils.py +0 -0
  50. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/test_version_manager.py +0 -0
  51. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/tests/tests.py +0 -0
  52. {python_package_folder-4.1.0 → python_package_folder-4.1.1}/uv.lock +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: python-package-folder
3
- Version: 4.1.0
3
+ Version: 4.1.1
4
4
  Summary: Python package to automatically package and build a folder, fetching all relevant dependencies.
5
5
  Project-URL: Repository, https://github.com/alelom/python-package-folder
6
6
  Author-email: Alessio Lombardi <work@alelom.com>
@@ -14,7 +14,7 @@
14
14
  <g fill="#fff" text-anchor="middle" font-family="DejaVu Sans,Verdana,Geneva,sans-serif" font-size="11">
15
15
  <text x="31.5" y="15" fill="#010101" fill-opacity=".3">coverage</text>
16
16
  <text x="31.5" y="14">coverage</text>
17
- <text x="81" y="15" fill="#010101" fill-opacity=".3">65%</text>
18
- <text x="81" y="14">65%</text>
17
+ <text x="81" y="15" fill="#010101" fill-opacity=".3">64%</text>
18
+ <text x="81" y="14">64%</text>
19
19
  </g>
20
20
  </svg>
@@ -42,7 +42,7 @@ dependencies = [
42
42
 
43
43
  # ---- Dev dependencies ----
44
44
 
45
- version = "4.1.0"
45
+ version = "4.1.1"
46
46
  [dependency-groups]
47
47
  dev = [
48
48
  "pytest>=8.3.5",
@@ -10,6 +10,8 @@ It can be invoked via:
10
10
 
11
11
  from __future__ import annotations
12
12
 
13
+ import os
14
+ import shutil
13
15
  import subprocess
14
16
  import sys
15
17
  from pathlib import Path
@@ -23,13 +25,23 @@ from .manager import BuildManager
23
25
  from .utils import find_project_root, find_source_directory
24
26
 
25
27
 
28
+ def is_github_actions() -> bool:
29
+ """Check if running in GitHub Actions."""
30
+ return os.getenv("GITHUB_ACTIONS") == "true"
31
+
32
+
33
+ def check_node_available() -> bool:
34
+ """Check if Node.js is available."""
35
+ return shutil.which("node") is not None
36
+
37
+
26
38
  def resolve_version_via_semantic_release(
27
39
  project_root: Path,
28
40
  subfolder_path: Path | None = None,
29
41
  package_name: str | None = None,
30
42
  repository: str | None = None,
31
43
  repository_url: str | None = None,
32
- ) -> str | None:
44
+ ) -> tuple[str | None, str | None]:
33
45
  """
34
46
  Resolve the next version using semantic-release via Node.js script.
35
47
 
@@ -41,8 +53,34 @@ def resolve_version_via_semantic_release(
41
53
  repository_url: Optional repository URL (required for Azure Artifacts)
42
54
 
43
55
  Returns:
44
- Version string if a release is determined, None if no release or error
56
+ Tuple of (version string if a release is determined, error message if any)
57
+ Returns (None, None) if no release or no error, (None, error_msg) on error
45
58
  """
59
+ # Note: Node.js availability should be checked before calling this function
60
+ # This check is a safety fallback
61
+ if not check_node_available():
62
+ if is_github_actions():
63
+ error_msg = """Node.js is not available in this GitHub Actions workflow.
64
+
65
+ To fix this, add the following steps BEFORE running python-package-folder:
66
+
67
+ - name: Setup Node.js
68
+ uses: actions/setup-node@v4
69
+ with:
70
+ node-version: '20'
71
+
72
+ - name: Install semantic-release
73
+ run: |
74
+ npm install -g semantic-release semantic-release-commit-filter
75
+
76
+ Alternatively, provide --version explicitly to skip automatic version resolution."""
77
+ print(f"Error: {error_msg}", file=sys.stderr)
78
+ return None, error_msg
79
+ else:
80
+ error_msg = "Node.js not found. Cannot resolve version via semantic-release."
81
+ print(f"Error: {error_msg}", file=sys.stderr)
82
+ return None, error_msg
83
+
46
84
  # Try to find the script in multiple locations:
47
85
  # 1. Project root / scripts (for development or when script is in repo)
48
86
  # 2. Package installation directory / scripts (for installed package)
@@ -90,7 +128,9 @@ def resolve_version_via_semantic_release(
90
128
  script_path = fallback_script
91
129
 
92
130
  if not script_path:
93
- return None
131
+ error_msg = "Could not locate get-next-version.cjs script"
132
+ print(f"Error: {error_msg}", file=sys.stderr)
133
+ return None, error_msg
94
134
 
95
135
  # Build command arguments
96
136
  cmd = ["node", str(script_path), str(project_root)]
@@ -123,38 +163,53 @@ def resolve_version_via_semantic_release(
123
163
  )
124
164
 
125
165
  if result.returncode != 0:
126
- # Log error details for debugging
166
+ # Collect error details
167
+ error_details = []
127
168
  if result.stderr:
128
- print(
129
- f"Warning: semantic-release version resolution failed: {result.stderr}",
130
- file=sys.stderr,
131
- )
132
- elif result.stdout:
133
- print(
134
- f"Warning: semantic-release version resolution failed: {result.stdout}",
135
- file=sys.stderr,
136
- )
137
- return None
169
+ error_details.append(f"stderr: {result.stderr}")
170
+ if result.stdout:
171
+ error_details.append(f"stdout: {result.stdout}")
172
+
173
+ error_msg = "semantic-release version resolution failed"
174
+ if error_details:
175
+ error_msg += f": {'; '.join(error_details)}"
176
+
177
+ print(f"Error: {error_msg}", file=sys.stderr)
178
+ return None, error_msg
138
179
 
139
180
  version = result.stdout.strip()
140
181
  if version and version != "none":
141
- return version
182
+ return version, None
142
183
 
143
- return None
184
+ return None, None
144
185
  except FileNotFoundError:
145
- # Node.js not found
146
- print(
147
- "Warning: Node.js not found. Cannot resolve version via semantic-release.",
148
- file=sys.stderr,
149
- )
150
- return None
186
+ # Node.js not found (shouldn't happen if check_node_available() passed, but handle gracefully)
187
+ if is_github_actions():
188
+ error_msg = """Node.js is not available in this GitHub Actions workflow.
189
+
190
+ To fix this, add the following steps BEFORE running python-package-folder:
191
+
192
+ - name: Setup Node.js
193
+ uses: actions/setup-node@v4
194
+ with:
195
+ node-version: '20'
196
+
197
+ - name: Install semantic-release
198
+ run: |
199
+ npm install -g semantic-release semantic-release-commit-filter
200
+
201
+ Alternatively, provide --version explicitly to skip automatic version resolution."""
202
+ print(f"Error: {error_msg}", file=sys.stderr)
203
+ return None, error_msg
204
+ else:
205
+ error_msg = "Node.js not found. Cannot resolve version via semantic-release."
206
+ print(f"Error: {error_msg}", file=sys.stderr)
207
+ return None, error_msg
151
208
  except Exception as e:
152
209
  # Other errors (e.g., permission issues, script not found)
153
- print(
154
- f"Warning: Error resolving version via semantic-release: {e}",
155
- file=sys.stderr,
156
- )
157
- return None
210
+ error_msg = f"Error resolving version via semantic-release: {e}"
211
+ print(f"Error: {error_msg}", file=sys.stderr)
212
+ return None, error_msg
158
213
  finally:
159
214
  # Clean up temporary file if we extracted from zip/pex
160
215
  # This must be at function level to ensure cleanup even on early return
@@ -311,6 +366,46 @@ def main() -> int:
311
366
  # Version is needed for subfolder builds or when publishing main package
312
367
  if is_subfolder or args.publish:
313
368
  print("No --version provided, attempting to resolve via semantic-release...")
369
+
370
+ # Check Node.js availability upfront
371
+ if not check_node_available():
372
+ if is_github_actions():
373
+ error_msg = """Node.js is not available in this GitHub Actions workflow.
374
+
375
+ To fix this, add the following steps BEFORE running python-package-folder:
376
+
377
+ - name: Setup Node.js
378
+ uses: actions/setup-node@v4
379
+ with:
380
+ node-version: '20'
381
+
382
+ - name: Install semantic-release
383
+ run: |
384
+ npm install -g semantic-release semantic-release-commit-filter
385
+
386
+ Alternatively, provide --version explicitly to skip automatic version resolution."""
387
+ print(f"Error: {error_msg}", file=sys.stderr)
388
+ else:
389
+ print(
390
+ "Error: Node.js is not available. Cannot resolve version via semantic-release.",
391
+ file=sys.stderr,
392
+ )
393
+ print(
394
+ "Please install Node.js or provide --version explicitly.",
395
+ file=sys.stderr,
396
+ )
397
+ return 1
398
+
399
+ # Log that Node.js is available (for debugging)
400
+ node_version = subprocess.run(
401
+ ["node", "--version"],
402
+ capture_output=True,
403
+ text=True,
404
+ check=False,
405
+ )
406
+ if node_version.returncode == 0:
407
+ print(f"Node.js detected: {node_version.stdout.strip()}")
408
+
314
409
  # Get repository info if publishing
315
410
  repository = args.publish if args.publish else None
316
411
  repository_url = args.repository_url if args.publish else None
@@ -322,7 +417,7 @@ def main() -> int:
322
417
  " ", "-"
323
418
  ).lower().strip("-")
324
419
  subfolder_rel_path = src_dir.relative_to(project_root)
325
- resolved_version = resolve_version_via_semantic_release(
420
+ resolved_version, error_details = resolve_version_via_semantic_release(
326
421
  project_root,
327
422
  subfolder_rel_path,
328
423
  package_name,
@@ -344,7 +439,7 @@ def main() -> int:
344
439
  except Exception:
345
440
  pass
346
441
 
347
- resolved_version = resolve_version_via_semantic_release(
442
+ resolved_version, error_details = resolve_version_via_semantic_release(
348
443
  project_root,
349
444
  subfolder_path=None,
350
445
  package_name=package_name_for_registry,
@@ -360,8 +455,11 @@ def main() -> int:
360
455
  "This could mean:\n"
361
456
  " - No release is needed (no relevant commits)\n"
362
457
  " - semantic-release is not installed or configured\n"
363
- " - Node.js is not available\n\n"
364
- "Please either:\n"
458
+ )
459
+ if error_details:
460
+ error_msg += f"\nDetails: {error_details}\n"
461
+ error_msg += (
462
+ "\nPlease either:\n"
365
463
  " - Install semantic-release: npm install -g semantic-release"
366
464
  )
367
465
  if is_subfolder: