dayhoff-tools 1.14.13__tar.gz → 1.14.15__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 (76) hide show
  1. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/PKG-INFO +2 -3
  2. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/finalize.py +25 -12
  3. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/utility_commands.py +32 -149
  4. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/pyproject.toml +24 -47
  5. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/README.md +0 -0
  6. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/__init__.py +0 -0
  7. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/batch/__init__.py +0 -0
  8. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/batch/workers/__init__.py +0 -0
  9. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/batch/workers/base.py +0 -0
  10. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/batch/workers/boltz.py +0 -0
  11. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/batch/workers/embed_t5.py +0 -0
  12. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/chemistry/standardizer.py +0 -0
  13. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/chemistry/utils.py +0 -0
  14. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/__init__.py +0 -0
  15. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/__init__.py +0 -0
  16. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/aws_batch.py +0 -0
  17. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/__init__.py +0 -0
  18. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/boltz.py +0 -0
  19. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/cancel.py +0 -0
  20. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/clean.py +0 -0
  21. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/embed_t5.py +0 -0
  22. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/list_jobs.py +0 -0
  23. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/local.py +0 -0
  24. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/logs.py +0 -0
  25. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/retry.py +0 -0
  26. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/status.py +0 -0
  27. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/commands/submit.py +0 -0
  28. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/job_id.py +0 -0
  29. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/batch/manifest.py +0 -0
  30. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/cloud_commands.py +0 -0
  31. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engine1/__init__.py +0 -0
  32. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engine1/engine_core.py +0 -0
  33. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engine1/engine_lifecycle.py +0 -0
  34. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engine1/engine_maintenance.py +0 -0
  35. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engine1/engine_management.py +0 -0
  36. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engine1/shared.py +0 -0
  37. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engine1/studio_commands.py +0 -0
  38. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/__init__.py +0 -0
  39. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/api_client.py +0 -0
  40. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/auth.py +0 -0
  41. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/engine-studio-cli.md +0 -0
  42. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/engine_commands.py +0 -0
  43. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/progress.py +0 -0
  44. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/simulators/cli-simulators.md +0 -0
  45. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/simulators/demo.sh +0 -0
  46. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/simulators/engine_list_simulator.py +0 -0
  47. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/simulators/engine_status_simulator.py +0 -0
  48. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/simulators/idle_status_simulator.py +0 -0
  49. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/simulators/simulator_utils.py +0 -0
  50. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/simulators/studio_list_simulator.py +0 -0
  51. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/simulators/studio_status_simulator.py +0 -0
  52. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/ssh_config.py +0 -0
  53. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/engines_studios/studio_commands.py +0 -0
  54. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/github_commands.py +0 -0
  55. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/main.py +0 -0
  56. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/cli/swarm_commands.py +0 -0
  57. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/deployment/base.py +0 -0
  58. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/deployment/deploy_aws.py +0 -0
  59. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/deployment/deploy_gcp.py +0 -0
  60. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/deployment/deploy_utils.py +0 -0
  61. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/deployment/job_runner.py +0 -0
  62. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/deployment/processors.py +0 -0
  63. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/deployment/swarm.py +0 -0
  64. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/embedders.py +0 -0
  65. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/fasta.py +0 -0
  66. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/file_ops.py +0 -0
  67. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/h5.py +0 -0
  68. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/intake/gcp.py +0 -0
  69. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/intake/gtdb.py +0 -0
  70. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/intake/kegg.py +0 -0
  71. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/intake/mmseqs.py +0 -0
  72. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/intake/structure.py +0 -0
  73. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/intake/uniprot.py +0 -0
  74. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/logs.py +0 -0
  75. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/sqlite.py +0 -0
  76. {dayhoff_tools-1.14.13 → dayhoff_tools-1.14.15}/dayhoff_tools/warehouse.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: dayhoff-tools
3
- Version: 1.14.13
3
+ Version: 1.14.15
4
4
  Summary: Common tools for all the repos at Dayhoff Labs
5
5
  Author: Daniel Martin-Alarcon
6
6
  Author-email: dma@dayhofflabs.com
@@ -25,7 +25,7 @@ Requires-Dist: fair-esm (>=2.0.0) ; extra == "full"
25
25
  Requires-Dist: firebase-admin (>=6.5.0)
26
26
  Requires-Dist: h5py (>=3.11.0) ; extra == "full"
27
27
  Requires-Dist: h5py (>=3.13.0) ; extra == "embedders"
28
- Requires-Dist: numpy (>=1.26.4) ; extra == "embedders"
28
+ Requires-Dist: numpy (>=1.26.4,<2.0) ; extra == "embedders"
29
29
  Requires-Dist: pandas (>=2.2.0,<2.2.3) ; extra == "embedders"
30
30
  Requires-Dist: pandas (>=2.2.0,<2.2.3) ; extra == "full"
31
31
  Requires-Dist: pydantic (>=2.0.0) ; extra == "batch"
@@ -38,7 +38,6 @@ Requires-Dist: sentencepiece (>=0.2.0) ; extra == "embedders"
38
38
  Requires-Dist: sentencepiece (>=0.2.0) ; extra == "full"
39
39
  Requires-Dist: sqlalchemy (>=2.0.40,<3.0.0) ; extra == "full"
40
40
  Requires-Dist: toml (>=0.10)
41
- Requires-Dist: torch (>=2.4.0) ; extra == "embedders"
42
41
  Requires-Dist: tqdm (>=4.67.1) ; extra == "embedders"
43
42
  Requires-Dist: tqdm (>=4.67.1) ; extra == "full"
44
43
  Requires-Dist: transformers (==4.36.2) ; extra == "full"
@@ -34,8 +34,13 @@ from ..manifest import (
34
34
  is_flag=True,
35
35
  help="For Boltz: copy entire output directory (default: only essential files)",
36
36
  )
37
+ @click.option(
38
+ "--skip-dedup",
39
+ is_flag=True,
40
+ help="Skip deduplication step (use if input has no duplicates)",
41
+ )
37
42
  @click.option("--base-path", default=BATCH_JOBS_BASE, help="Base path for job data")
38
- def finalize(job_id, output, force, keep_intermediates, full_output, base_path):
43
+ def finalize(job_id, output, force, keep_intermediates, full_output, skip_dedup, base_path):
39
44
  """Combine results and clean up job intermediates.
40
45
 
41
46
  For embedding jobs, combines H5 files into a single output file.
@@ -46,6 +51,9 @@ def finalize(job_id, output, force, keep_intermediates, full_output, base_path):
46
51
  # Embedding job - combine H5 files
47
52
  dh batch finalize dma-embed-20260109-a3f2 --output /primordial/embeddings.h5
48
53
 
54
+ # Skip deduplication (faster if input has no duplicates)
55
+ dh batch finalize dma-embed-20260109-a3f2 --output /primordial/embeddings.h5 --skip-dedup
56
+
49
57
  # Boltz job - extract essential files only (default)
50
58
  dh batch finalize dma-boltz-20260113-190a --output /primordial/structures/
51
59
 
@@ -92,7 +100,7 @@ def finalize(job_id, output, force, keep_intermediates, full_output, base_path):
92
100
  # Finalize based on pipeline type
93
101
  click.echo()
94
102
  if manifest.pipeline in ("embed-t5", "embed"):
95
- _finalize_embeddings(output_dir, output_path)
103
+ _finalize_embeddings(output_dir, output_path, skip_dedup=skip_dedup)
96
104
  elif manifest.pipeline == "boltz":
97
105
  _finalize_boltz(output_dir, output_path, full_output=full_output)
98
106
  else:
@@ -182,7 +190,7 @@ def _check_completion(job_id: str, base_path: str) -> list[int]:
182
190
  return incomplete
183
191
 
184
192
 
185
- def _finalize_embeddings(output_dir: Path, output_path: Path):
193
+ def _finalize_embeddings(output_dir: Path, output_path: Path, skip_dedup: bool = False):
186
194
  """Combine H5 embedding files into a single output."""
187
195
  h5_files = sorted(output_dir.glob("embed_*.h5"))
188
196
 
@@ -191,6 +199,8 @@ def _finalize_embeddings(output_dir: Path, output_path: Path):
191
199
  raise SystemExit(1)
192
200
 
193
201
  click.echo(f"Found {len(h5_files)} H5 files to combine")
202
+ if skip_dedup:
203
+ click.echo("Skipping deduplication (--skip-dedup)")
194
204
 
195
205
  # Check if output already exists
196
206
  if output_path.exists():
@@ -213,10 +223,9 @@ def _finalize_embeddings(output_dir: Path, output_path: Path):
213
223
  click.echo("Single chunk - copying directly...")
214
224
  shutil.copy2(h5_files[0], output_path)
215
225
  else:
216
- # Multiple files - combine, deduplicate, and optimize
226
+ # Multiple files - combine and optionally deduplicate
217
227
  with tempfile.TemporaryDirectory() as tmpdir:
218
228
  combined_path = Path(tmpdir) / "combined.h5"
219
- deduped_path = Path(tmpdir) / "deduped.h5"
220
229
 
221
230
  # Combine H5 files
222
231
  click.echo("Combining H5 files...")
@@ -226,13 +235,17 @@ def _finalize_embeddings(output_dir: Path, output_path: Path):
226
235
  output_file=str(combined_path),
227
236
  )
228
237
 
229
- # Deduplicate
230
- click.echo("Deduplicating...")
231
- deduplicate_h5_file(str(combined_path), str(deduped_path))
232
-
233
- # Optimize chunks
234
- click.echo("Optimizing chunks...")
235
- optimize_protein_embedding_chunks(str(deduped_path), str(output_path))
238
+ if skip_dedup:
239
+ # Skip dedup - optimize directly from combined
240
+ click.echo("Optimizing chunks...")
241
+ optimize_protein_embedding_chunks(str(combined_path), str(output_path))
242
+ else:
243
+ # Full pipeline: combine -> dedup -> optimize
244
+ deduped_path = Path(tmpdir) / "deduped.h5"
245
+ click.echo("Deduplicating...")
246
+ deduplicate_h5_file(str(combined_path), str(deduped_path))
247
+ click.echo("Optimizing chunks...")
248
+ optimize_protein_embedding_chunks(str(deduped_path), str(output_path))
236
249
 
237
250
  click.echo(click.style("✓ H5 files combined successfully", fg="green"))
238
251
 
@@ -110,24 +110,11 @@ def build_and_upload_wheel(bump_part: str = "patch"):
110
110
  publish_cmd = ["uv", "publish", "--token", token]
111
111
  print("Using UV_PUBLISH_TOKEN for authentication.")
112
112
 
113
- # Find the primary manifest (prefer AWS, then Mac, then Workstation)
114
- pyproject_path = None
115
- for candidate in [
116
- "pyproject.aws.toml",
117
- "pyproject.mac.toml",
118
- "pyproject.workstation.toml",
119
- ]:
120
- if Path(candidate).exists():
121
- pyproject_path = candidate
122
- break
123
-
124
- if not pyproject_path:
125
- print(
126
- "Error: No platform-specific manifest found (pyproject.aws.toml, pyproject.mac.toml, or pyproject.workstation.toml)"
127
- )
113
+ # Use standard pyproject.toml
114
+ pyproject_path = "pyproject.toml"
115
+ if not Path(pyproject_path).exists():
116
+ print("Error: pyproject.toml not found in current directory.")
128
117
  return
129
-
130
- print(f"Using manifest: {pyproject_path}")
131
118
  current_version = None # Initialize in case the first try block fails
132
119
 
133
120
  try:
@@ -190,90 +177,33 @@ def build_and_upload_wheel(bump_part: str = "patch"):
190
177
  f.write(new_content)
191
178
  print(f"Updated {pyproject_path} with version {new_version}")
192
179
 
193
- # Mirror version in all other platform manifests (best-effort)
194
- other_manifests = []
195
- for candidate in [
196
- "pyproject.aws.toml",
197
- "pyproject.mac.toml",
198
- "pyproject.workstation.toml",
199
- ]:
200
- if Path(candidate).exists() and candidate != pyproject_path:
201
- other_manifests.append(Path(candidate))
202
-
203
- for manifest_path in other_manifests:
204
- try:
205
- content = manifest_path.read_text()
206
- pattern = re.compile(
207
- f'^version\s*=\s*"{re.escape(current_version)}"', re.MULTILINE
208
- )
209
- new_content, replacements = pattern.subn(
210
- f'version = "{new_version}"', content
211
- )
212
- if replacements > 0:
213
- manifest_path.write_text(new_content)
214
- print(f"Updated {manifest_path} with version {new_version}")
215
- except Exception as e:
216
- print(f"Warning: Could not update {manifest_path}: {e}")
217
180
  # --- End Version Bumping Logic ---
218
181
 
219
182
  # Build wheel and sdist
220
- # UV expects pyproject.toml, so temporarily copy the platform manifest
221
- backup_created = False
222
- temp_pyproject_created = False
223
- if pyproject_path != "pyproject.toml":
224
- if Path("pyproject.toml").exists():
225
- Path("pyproject.toml").rename("pyproject.toml.build.bak")
226
- backup_created = True
227
- Path(pyproject_path).read_text()
228
- with open("pyproject.toml", "w") as f:
229
- f.write(Path(pyproject_path).read_text())
230
- temp_pyproject_created = True
183
+ build_cmd = ["uv", "build"]
184
+ print(f"Running command: {BLUE}{' '.join(build_cmd)}{RESET}")
185
+ subprocess.run(build_cmd, check=True)
231
186
 
232
- try:
233
- build_cmd = ["uv", "build"]
234
- # Print command in blue
235
- print(f"Running command: {BLUE}{' '.join(build_cmd)}{RESET}")
236
- subprocess.run(build_cmd, check=True)
237
-
238
- # Upload using uv publish with explicit arguments
239
- # Print masked command in blue
240
- print(f"Running command: {BLUE}{' '.join(publish_cmd_safe_print)}{RESET}")
241
- subprocess.run(
242
- publish_cmd, # Use the actual command with token
243
- check=True,
244
- )
187
+ # Upload to PyPI
188
+ print(f"Running command: {BLUE}{' '.join(publish_cmd_safe_print)}{RESET}")
189
+ subprocess.run(publish_cmd, check=True)
245
190
 
246
- print(f"Successfully built and uploaded version {new_version} to PyPI")
191
+ print(f"Successfully built and uploaded version {new_version} to PyPI")
247
192
 
248
- # Re-install DHT in current venv when building from DHT itself
249
- # (Keep temp pyproject.toml until after this step)
250
- try:
251
- proj_name = None
252
- try:
253
- proj_toml = toml.load(pyproject_path)
254
- proj_name = (
255
- proj_toml.get("project", {}).get("name")
256
- if isinstance(proj_toml, dict)
257
- else None
258
- )
259
- except Exception:
260
- pass
261
- if proj_name == "dayhoff-tools":
262
- print("Re-installing dayhoff-tools into the active environment…")
263
- reinstall_cmd = ["uv", "pip", "install", "-e", ".[full]"]
264
- print(f"Running command: {BLUE}{' '.join(reinstall_cmd)}{RESET}")
265
- subprocess.run(reinstall_cmd, check=True)
266
- print("dayhoff-tools reinstalled in the current environment.")
267
- except subprocess.CalledProcessError as e:
268
- print(f"Warning: Failed to reinstall dayhoff-tools locally: {e}")
269
-
270
- finally:
271
- # Restore original state (always clean up, even if errors occurred)
272
- if temp_pyproject_created:
273
- if Path("pyproject.toml").exists():
274
- Path("pyproject.toml").unlink()
275
- if backup_created and Path("pyproject.toml.build.bak").exists():
276
- Path("pyproject.toml.build.bak").rename("pyproject.toml")
193
+ # Re-install DHT in Pixi environment when building from DHT itself
194
+ try:
195
+ proj_toml = toml.load(pyproject_path)
196
+ proj_name = proj_toml.get("project", {}).get("name")
197
+ if proj_name == "dayhoff-tools":
198
+ print("Re-installing dayhoff-tools into the Pixi environment...")
199
+ reinstall_cmd = ["pixi", "install"]
200
+ print(f"Running command: {BLUE}{' '.join(reinstall_cmd)}{RESET}")
201
+ subprocess.run(reinstall_cmd, check=True)
202
+ print("dayhoff-tools reinstalled in the Pixi environment.")
203
+ except subprocess.CalledProcessError as e:
204
+ print(f"Warning: Failed to reinstall dayhoff-tools locally: {e}")
205
+ except Exception:
206
+ pass # Not dayhoff-tools or couldn't read toml
277
207
 
278
208
  except FileNotFoundError:
279
209
  print(f"Error: {pyproject_path} not found.")
@@ -304,42 +234,18 @@ def build_and_upload_wheel(bump_part: str = "patch"):
304
234
  f"Warning: Could not find version {new_version} to revert in {pyproject_path}."
305
235
  )
306
236
 
307
- # Also revert other platform manifests
308
- for candidate in [
309
- "pyproject.aws.toml",
310
- "pyproject.mac.toml",
311
- "pyproject.workstation.toml",
312
- ]:
313
- if Path(candidate).exists() and candidate != pyproject_path:
314
- try:
315
- content_revert = Path(candidate).read_text()
316
- reverted, num = pattern_revert.subn(
317
- f'version = "{current_version}"', content_revert
318
- )
319
- if num > 0:
320
- Path(candidate).write_text(reverted)
321
- print(f"Successfully reverted version in {candidate}.")
322
- except Exception as e2:
323
- print(
324
- f"Warning: Failed to revert version change in {candidate}: {e2}"
325
- )
326
237
  except Exception as revert_e:
327
- print(
328
- f"Warning: Failed to revert version change in {pyproject_path}: {revert_e}"
329
- )
238
+ print(f"Warning: Failed to revert version change: {revert_e}")
330
239
  except Exception as e:
331
240
  print(f"An unexpected error occurred: {e}")
332
- # Also attempt rollback here if version was bumped
241
+ # Attempt rollback if version was bumped
333
242
  if current_version and "new_version" in locals() and new_version:
334
243
  try:
335
- print(
336
- f"Attempting to revert version in {pyproject_path} back to {current_version} due to unexpected error..."
337
- )
338
- # (Same revert logic as above)
244
+ print(f"Attempting to revert version back to {current_version}...")
339
245
  with open(pyproject_path, "r") as f:
340
246
  content_revert = f.read()
341
247
  pattern_revert = re.compile(
342
- f'^version\s*=\s*"{re.escape(new_version)}"', re.MULTILINE
248
+ f'^version\\s*=\\s*"{re.escape(new_version)}"', re.MULTILINE
343
249
  )
344
250
  reverted_content, num_revert = pattern_revert.subn(
345
251
  f'version = "{current_version}"', content_revert
@@ -347,34 +253,11 @@ def build_and_upload_wheel(bump_part: str = "patch"):
347
253
  if num_revert > 0:
348
254
  with open(pyproject_path, "w") as f:
349
255
  f.write(reverted_content)
350
- print(f"Successfully reverted version in {pyproject_path}.")
256
+ print("Successfully reverted version in pyproject.toml.")
351
257
  else:
352
- print(
353
- f"Warning: Could not find version {new_version} to revert in {pyproject_path}."
354
- )
355
- # Also revert other platform manifests
356
- for candidate in [
357
- "pyproject.aws.toml",
358
- "pyproject.mac.toml",
359
- "pyproject.workstation.toml",
360
- ]:
361
- if Path(candidate).exists() and candidate != pyproject_path:
362
- try:
363
- content_revert = Path(candidate).read_text()
364
- reverted, num = pattern_revert.subn(
365
- f'version = "{current_version}"', content_revert
366
- )
367
- if num > 0:
368
- Path(candidate).write_text(reverted)
369
- print(f"Successfully reverted version in {candidate}.")
370
- except Exception as e2:
371
- print(
372
- f"Warning: Failed to revert version change in {candidate}: {e2}"
373
- )
258
+ print(f"Warning: Could not find version {new_version} to revert.")
374
259
  except Exception as revert_e:
375
- print(
376
- f"Warning: Failed to revert version change in {pyproject_path}: {revert_e}"
377
- )
260
+ print(f"Warning: Failed to revert version change: {revert_e}")
378
261
 
379
262
 
380
263
  # --- Dependency Management Commands ---
@@ -1,96 +1,73 @@
1
- # This block is needed because we package DHT for PyPi.
1
+ # =============================================================================
2
+ # DAYHOFF-TOOLS: Package Configuration
3
+ # =============================================================================
4
+ # This file defines the package for PyPI distribution and editable installs.
5
+ # Development environment is managed by pixi.toml, NOT this file.
6
+ # =============================================================================
7
+
2
8
  [build-system]
3
9
  requires = ["poetry-core>=2.0"]
4
10
  build-backend = "poetry.core.masonry.api"
5
11
 
6
12
  [project]
7
13
  name = "dayhoff-tools"
8
- version = "1.14.13"
14
+ version = "1.14.15"
9
15
  description = "Common tools for all the repos at Dayhoff Labs"
10
16
  authors = [
11
17
  {name = "Daniel Martin-Alarcon", email = "dma@dayhofflabs.com"}
12
18
  ]
13
19
  readme = "README.md"
20
+ requires-python = ">=3.10,<4.0"
14
21
 
22
+ # Core dependencies - minimal set for basic CLI functionality
15
23
  dependencies = [
24
+ "boto3>=1.36.8",
16
25
  "firebase-admin>=6.5.0",
17
26
  "pyyaml>=6.0",
27
+ "questionary>=2.0.1",
18
28
  "requests>=2.31.0",
19
- "typer>=0.9.0",
20
29
  "toml>=0.10",
21
- "questionary>=2.0.1",
30
+ "typer>=0.9.0",
22
31
  "tzdata>=2025.2",
23
- "boto3>=1.36.8",
24
32
  ]
25
- requires-python = ">=3.10,<4.0"
26
33
 
27
34
  [project.optional-dependencies]
35
+ # Full set of optional dependencies for all features
28
36
  full = [
29
37
  "biopython>=1.84",
30
38
  "docker>=7.1.0",
31
39
  "fair-esm>=2.0.0",
32
40
  "h5py>=3.11.0",
33
- "pandas (>=2.2.0,<2.2.3)",
41
+ "pandas>=2.2.0,<2.2.3",
34
42
  "rdkit-pypi>=2022.9.5",
35
- "sqlalchemy (>=2.0.40,<3.0.0)",
36
- "transformers==4.36.2",
37
43
  "sentencepiece>=0.2.0",
44
+ "sqlalchemy>=2.0.40,<3.0.0",
38
45
  "tqdm>=4.67.1",
46
+ "transformers==4.36.2",
39
47
  ]
48
+
49
+ # Embedding models (requires torch - user must install separately for their platform)
40
50
  embedders = [
41
51
  "biopython>=1.85",
42
52
  "fair-esm>=2.0.0",
43
53
  "h5py>=3.13.0",
44
- "numpy>=1.26.4",
45
- "pandas (>=2.2.0,<2.2.3)",
54
+ "numpy>=1.26.4,<2.0",
55
+ "pandas>=2.2.0,<2.2.3",
46
56
  "sentencepiece>=0.2.0",
47
- "torch>=2.4.0",
48
57
  "tqdm>=4.67.1",
49
58
  "transformers>=4.36.2",
50
59
  ]
51
- # Boltz structure prediction dependencies
60
+
61
+ # Boltz structure prediction
52
62
  boltz = [
53
63
  "ruamel.yaml>=0.17.0",
54
64
  ]
65
+
55
66
  # Batch job system (CLI and worker utilities)
56
67
  batch = [
57
68
  "click>=8.0.0",
58
69
  "pydantic>=2.0.0",
59
70
  ]
60
71
 
61
- [[tool.uv.index]]
62
- name = "torch-cuda"
63
- url = "https://download.pytorch.org/whl/cu121"
64
- explicit = true
65
-
66
- [tool.uv.sources]
67
- torch = { index = "torch-cuda" }
68
- torchvision = { index = "torch-cuda" }
69
-
70
- [dependency-groups]
71
- dev = [
72
- "black>=25.1.0,<26",
73
- "boto3>=1.36.8",
74
- "colorlog>=6.8.2,<7",
75
- "docker>=7.1.0",
76
- "dvc>=3.48.2,<4",
77
- "dvc-gs>=3.0.1,<4",
78
- "flake8>=7.0.0,<8",
79
- "google-cloud-storage>=2.14.0",
80
- "ipykernel>=6.29.5,<7",
81
- "ipywidgets>=8.1.3,<9",
82
- "isort>=5.13.2,<6",
83
- "nbformat>=5.10.4",
84
- "numpy<2.0.0",
85
- "pandas (>=2.2.0,<2.2.3)",
86
- "pylance>=0.10.2,<1",
87
- "pylint>=3.1.0,<4",
88
- "pytest>=8.0.2,<9",
89
- "pytest-cov>=4.1.0,<5",
90
- "pytest-mock>=3.12.0,<4",
91
- "torch==2.4.0+cu121",
92
- "torchvision==0.19.0+cu121",
93
- ]
94
-
95
72
  [project.scripts]
96
73
  dh = "dayhoff_tools.cli.main:app"