machineconfig 5.82__py3-none-any.whl → 5.83__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.

Potentially problematic release.


This version of machineconfig might be problematic. Click here for more details.

@@ -1,4 +1,4 @@
1
- from typing import Optional, Any, Union
1
+ from typing import Callable, Optional, Any, Union
2
2
  import os
3
3
  from pathlib import Path
4
4
  import rich.console
@@ -6,7 +6,7 @@ from machineconfig.utils.terminal import Response, MACHINE
6
6
  from machineconfig.utils.accessories import pprint
7
7
 
8
8
  UV_RUN_CMD = "$HOME/.local/bin/uv run"
9
- MACHINECONFIG_VERSION = """ "machineconfig>=5.74" """
9
+ MACHINECONFIG_VERSION = "machineconfig>=5.74"
10
10
  DEFAULT_PICKLE_SUBDIR = "tmp_results/tmp_scripts/ssh"
11
11
 
12
12
 
@@ -186,15 +186,32 @@ class SSH:
186
186
  res.capture().print_if_unsuccessful(desc=description, strict_err=strict_stderr, strict_returncode=strict_return_code, assert_success=False)
187
187
  self.terminal_responses.append(res)
188
188
  return res
189
- def run_py(self, python_code: str, description: str, verbose_output: bool, strict_stderr: bool, strict_return_code: bool) -> Response:
189
+ def run_py(self, python_code: str, dependencies: list[str], venv_path: Optional[str],
190
+ description: str, verbose_output: bool, strict_stderr: bool, strict_return_code: bool) -> Response:
190
191
  from machineconfig.utils.accessories import randstr
191
192
  cmd_path = Path.home().joinpath(f"{DEFAULT_PICKLE_SUBDIR}/runpy_{randstr()}.py")
192
193
  cmd_path.parent.mkdir(parents=True, exist_ok=True)
193
194
  cmd_path.write_text(python_code, encoding="utf-8")
194
195
  self.copy_from_here(source_path=cmd_path, target_path=None, compress_with_zip=False, recursive=False, overwrite_existing=False)
195
- uv_cmd = f"""{UV_RUN_CMD} --with {MACHINECONFIG_VERSION} python {cmd_path.relative_to(Path.home())}"""
196
+ if len(dependencies) > 0:
197
+ with_clause = " --with " + '"', ",".join(dependencies) + '"'
198
+ else:
199
+ with_clause = ""
200
+ uv_cmd = f"""{UV_RUN_CMD} {with_clause} python {cmd_path.relative_to(Path.home())}"""
201
+ if venv_path is not None:
202
+ if self.get_remote_machine() == "Windows":
203
+ venv_export = f"$env:UV_PROJECT_ENVIRONMENT='{venv_path}';"
204
+ uv_cmd = venv_export + uv_cmd
205
+ else:
206
+ venv_export = f"UV_PROJECT_ENVIRONMENT={venv_path}"
207
+ uv_cmd = venv_export + " " + uv_cmd
196
208
  return self.run_shell(command=uv_cmd, verbose_output=verbose_output, description=description or f"run_py on {self.get_remote_repr(add_machine=False)}", strict_stderr=strict_stderr, strict_return_code=strict_return_code)
197
209
 
210
+ def run_py_func(self, func: Callable[..., Any], dependencies: list[str], venv_path: Optional[str]) -> Response:
211
+ from machineconfig.utils.meta import function_to_script
212
+ command = function_to_script(func=func, call_with_kwargs={})
213
+ return self.run_py(python_code=command, dependencies=dependencies, venv_path=venv_path, description=f"run_py_func {func.__name__} on {self.get_remote_repr(add_machine=False)}", verbose_output=True, strict_stderr=True, strict_return_code=True)
214
+
198
215
  def _simple_sftp_get(self, remote_path: str, local_path: Path) -> None:
199
216
  """Simple SFTP get without any recursion or path expansion - for internal use only."""
200
217
  if self.sftp is None:
@@ -225,7 +242,7 @@ class SSH:
225
242
  from machineconfig.utils.accessories import randstr
226
243
  remote_json_output = Path.home().joinpath(f"{DEFAULT_PICKLE_SUBDIR}/return_{randstr()}.json").as_posix()
227
244
  command = function_to_script(func=create_target_dir, call_with_kwargs={"target_dir_path": Path(target_path).as_posix(), "overwrite": overwrite_existing, "json_output_path": remote_json_output})
228
- response = self.run_py(python_code=command, description=f"Creating target directory `{Path(target_path).parent.as_posix()}` @ {self.get_remote_repr(add_machine=False)}", verbose_output=False, strict_stderr=False, strict_return_code=False)
245
+ response = self.run_py(python_code=command, dependencies=[MACHINECONFIG_VERSION], venv_path=None, description=f"Creating target directory `{Path(target_path).parent.as_posix()}` @ {self.get_remote_repr(add_machine=False)}", verbose_output=False, strict_stderr=False, strict_return_code=False)
229
246
  remote_json_path = response.op.strip()
230
247
  if not remote_json_path:
231
248
  raise RuntimeError(f"Failed to create target directory {target_path} - no response from remote")
@@ -308,7 +325,7 @@ class SSH:
308
325
  archive_path.unlink()
309
326
  from machineconfig.utils.meta import function_to_script
310
327
  command = function_to_script(func=unzip_archive, call_with_kwargs={"zip_file_path": remotepath.as_posix(), "overwrite_flag": overwrite_existing})
311
- _resp = self.run_py(python_code=command, description=f"UNZIPPING {remotepath.as_posix()}", verbose_output=False, strict_stderr=True, strict_return_code=True)
328
+ _resp = self.run_py(python_code=command, dependencies=[MACHINECONFIG_VERSION], venv_path=None, description=f"UNZIPPING {remotepath.as_posix()}", verbose_output=False, strict_stderr=True, strict_return_code=True)
312
329
  source_obj.unlink()
313
330
  print("\n")
314
331
  return source_obj
@@ -329,7 +346,7 @@ class SSH:
329
346
  from machineconfig.utils.accessories import randstr
330
347
  remote_json_output = Path.home().joinpath(f"{DEFAULT_PICKLE_SUBDIR}/return_{randstr()}.json").as_posix()
331
348
  command = function_to_script(func=check_is_dir, call_with_kwargs={"path_to_check": str(source_path), "json_output_path": remote_json_output})
332
- response = self.run_py(python_code=command, description=f"Check if source `{source_path}` is a dir", verbose_output=False, strict_stderr=False, strict_return_code=False)
349
+ response = self.run_py(python_code=command, dependencies=[MACHINECONFIG_VERSION], venv_path=None, description=f"Check if source `{source_path}` is a dir", verbose_output=False, strict_stderr=False, strict_return_code=False)
333
350
  remote_json_path = response.op.strip()
334
351
  if not remote_json_path:
335
352
  raise RuntimeError(f"Failed to check if {source_path} is directory - no response from remote")
@@ -363,7 +380,7 @@ class SSH:
363
380
  from machineconfig.utils.accessories import randstr
364
381
  remote_json_output = Path.home().joinpath(f"{DEFAULT_PICKLE_SUBDIR}/return_{randstr()}.json").as_posix()
365
382
  command = function_to_script(func=expand_source, call_with_kwargs={"path_to_expand": str(source_path), "json_output_path": remote_json_output})
366
- response = self.run_py(python_code=command, description="Resolving source path by expanding user", verbose_output=False, strict_stderr=False, strict_return_code=False)
383
+ response = self.run_py(python_code=command, dependencies=[MACHINECONFIG_VERSION], venv_path=None, description="Resolving source path by expanding user", verbose_output=False, strict_stderr=False, strict_return_code=False)
367
384
  remote_json_path = response.op.strip()
368
385
  if not remote_json_path:
369
386
  raise RuntimeError(f"Could not resolve source path {source_path} - no response from remote")
@@ -412,7 +429,7 @@ class SSH:
412
429
  from machineconfig.utils.accessories import randstr
413
430
  remote_json_output = Path.home().joinpath(f"{DEFAULT_PICKLE_SUBDIR}/return_{randstr()}.json").as_posix()
414
431
  command = function_to_script(func=search_files, call_with_kwargs={"directory_path": expanded_source, "json_output_path": remote_json_output})
415
- response = self.run_py(python_code=command, description="Searching for files in source", verbose_output=False, strict_stderr=False, strict_return_code=False)
432
+ response = self.run_py(python_code=command, dependencies=[MACHINECONFIG_VERSION], venv_path=None, description="Searching for files in source", verbose_output=False, strict_stderr=False, strict_return_code=False)
416
433
  remote_json_path = response.op.strip()
417
434
  if not remote_json_path:
418
435
  raise RuntimeError(f"Could not resolve source path {source} - no response from remote")
@@ -450,7 +467,7 @@ class SSH:
450
467
  from machineconfig.utils.accessories import randstr
451
468
  remote_json_output = Path.home().joinpath(f"{DEFAULT_PICKLE_SUBDIR}/return_{randstr()}.json").as_posix()
452
469
  command = function_to_script(func=collapse_to_home_dir, call_with_kwargs={"absolute_path": expanded_source, "json_output_path": remote_json_output})
453
- response = self.run_py(python_code=command, description="Finding default target via relative source path", verbose_output=False, strict_stderr=False, strict_return_code=False)
470
+ response = self.run_py(python_code=command, dependencies=[MACHINECONFIG_VERSION], venv_path=None, description="Finding default target via relative source path", verbose_output=False, strict_stderr=False, strict_return_code=False)
454
471
  remote_json_path_dir = response.op.strip()
455
472
  if not remote_json_path_dir:
456
473
  raise RuntimeError("Could not resolve target path - no response from remote")
@@ -502,7 +519,7 @@ class SSH:
502
519
  from machineconfig.utils.accessories import randstr
503
520
  remote_json_output = Path.home().joinpath(f"{DEFAULT_PICKLE_SUBDIR}/return_{randstr()}.json").as_posix()
504
521
  command = function_to_script(func=zip_source, call_with_kwargs={"path_to_zip": expanded_source, "json_output_path": remote_json_output})
505
- response = self.run_py(python_code=command, description=f"Zipping source file {source}", verbose_output=False, strict_stderr=False, strict_return_code=False)
522
+ response = self.run_py(python_code=command, dependencies=[MACHINECONFIG_VERSION], venv_path=None, description=f"Zipping source file {source}", verbose_output=False, strict_stderr=False, strict_return_code=False)
506
523
  remote_json_path = response.op.strip()
507
524
  if not remote_json_path:
508
525
  raise RuntimeError(f"Could not zip {source} - no response from remote")
@@ -541,7 +558,7 @@ class SSH:
541
558
  from machineconfig.utils.accessories import randstr
542
559
  remote_json_output = Path.home().joinpath(f"{DEFAULT_PICKLE_SUBDIR}/return_{randstr()}.json").as_posix()
543
560
  command = function_to_script(func=collapse_to_home, call_with_kwargs={"absolute_path": expanded_source, "json_output_path": remote_json_output})
544
- response = self.run_py(python_code=command, description="Finding default target via relative source path", verbose_output=False, strict_stderr=False, strict_return_code=False)
561
+ response = self.run_py(python_code=command, dependencies=[MACHINECONFIG_VERSION], venv_path=None, description="Finding default target via relative source path", verbose_output=False, strict_stderr=False, strict_return_code=False)
545
562
  remote_json_path = response.op.strip()
546
563
  if not remote_json_path:
547
564
  raise RuntimeError("Could not resolve target path - no response from remote")
@@ -597,7 +614,7 @@ class SSH:
597
614
 
598
615
  from machineconfig.utils.meta import function_to_script
599
616
  command = function_to_script(func=delete_temp_zip, call_with_kwargs={"path_to_delete": expanded_source})
600
- self.run_py(python_code=command, description="Cleaning temp zip files @ remote.", verbose_output=False, strict_stderr=True, strict_return_code=True)
617
+ self.run_py(python_code=command, dependencies=[MACHINECONFIG_VERSION], venv_path=None, description="Cleaning temp zip files @ remote.", verbose_output=False, strict_stderr=True, strict_return_code=True)
601
618
 
602
619
  print("\n")
603
620
  return target_obj
@@ -0,0 +1,20 @@
1
+ from typing import Callable, ParamSpec, TypeVar, Any, Dict
2
+
3
+ P = ParamSpec('P')
4
+ R = TypeVar('R')
5
+
6
+ def typed_function(func: Callable[P, R], signature_dict: Dict[str, Any]) -> Callable[P, R]:
7
+ """
8
+ Returns the function with its signature preserved using ParamSpec.
9
+
10
+ The signature_dict is passed for potential future use or documentation,
11
+ but is not currently used in the implementation.
12
+
13
+ Args:
14
+ func: The function whose signature is to be preserved.
15
+ signature_dict: A dictionary describing the function's signature (not used).
16
+
17
+ Returns:
18
+ The original function, typed with ParamSpec to preserve its signature.
19
+ """
20
+ return func
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: machineconfig
3
- Version: 5.82
3
+ Version: 5.83
4
4
  Summary: Dotfiles management package
5
5
  Author-email: Alex Al-Saffar <programmer@usa.com>
6
6
  License: Apache 2.0
@@ -396,8 +396,9 @@ machineconfig/utils/procs.py,sha256=w75oGKfR7FpT1pGTGd2XscnEOO0IHBWxohLbi69hLqg,
396
396
  machineconfig/utils/scheduler.py,sha256=jZ_1yghqA3-aINPRmE_76gboqJc0UElroR7urNOfXKs,14940
397
397
  machineconfig/utils/scheduling.py,sha256=RF1iXJpqf4Dg18jdZWtBixz97KAHC6VKYqTFSpdLWuc,11188
398
398
  machineconfig/utils/source_of_truth.py,sha256=ZAnCRltiM07ig--P6g9_6nEAvNFC4X4ERFTVcvpIYsE,764
399
- machineconfig/utils/ssh.py,sha256=l9ibxTbosLfzBHW0v4dbFN4xCA0jY9QPkB42CTDRCKI,37564
399
+ machineconfig/utils/ssh.py,sha256=GPSILaCLylRAaC5S_VWeXWbF5dHA4UqJ5Y9WaGBgNcQ,39101
400
400
  machineconfig/utils/terminal.py,sha256=IlmOByfQG-vjhaFFxxzU5rWzP5_qUzmalRfuey3PAmc,11801
401
+ machineconfig/utils/tst.py,sha256=6u1GI49NdcpxH2BYGAusNfY5q9G_ytCGVzFM5b6HYpM,674
401
402
  machineconfig/utils/upgrade_packages.py,sha256=H96zVJEWXJW07nh5vhjuSCrPtXGqoUb7xeJsFYYdmCI,3330
402
403
  machineconfig/utils/ve.py,sha256=L-6PBXnQGXThiwWgheJMQoisAZOZA6SVCbGw2J-GFnI,2414
403
404
  machineconfig/utils/ai/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -420,8 +421,8 @@ machineconfig/utils/schemas/installer/installer_types.py,sha256=QClRY61QaduBPJoS
420
421
  machineconfig/utils/schemas/layouts/layout_types.py,sha256=TcqlZdGVoH8htG5fHn1KWXhRdPueAcoyApppZsPAPto,2020
421
422
  machineconfig/utils/schemas/repos/repos_types.py,sha256=ECVr-3IVIo8yjmYmVXX2mnDDN1SLSwvQIhx4KDDQHBQ,405
422
423
  machineconfig/utils/ssh_utils/utils.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
423
- machineconfig-5.82.dist-info/METADATA,sha256=W-g65cG_kSWDmbuD43W0cu4-MJ6wsPuWI5WwEqKYdMM,3013
424
- machineconfig-5.82.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
425
- machineconfig-5.82.dist-info/entry_points.txt,sha256=M0jwN_brZdXWhmNVeXLvdKxfkv8WhhXFZYcuKBA9qnk,418
426
- machineconfig-5.82.dist-info/top_level.txt,sha256=porRtB8qms8fOIUJgK-tO83_FeH6Bpe12oUVC670teA,14
427
- machineconfig-5.82.dist-info/RECORD,,
424
+ machineconfig-5.83.dist-info/METADATA,sha256=RNto4CYGyV0EIXxxYQvZKuuZSTHaL9xcxtqiTYUgNTA,3013
425
+ machineconfig-5.83.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
426
+ machineconfig-5.83.dist-info/entry_points.txt,sha256=M0jwN_brZdXWhmNVeXLvdKxfkv8WhhXFZYcuKBA9qnk,418
427
+ machineconfig-5.83.dist-info/top_level.txt,sha256=porRtB8qms8fOIUJgK-tO83_FeH6Bpe12oUVC670teA,14
428
+ machineconfig-5.83.dist-info/RECORD,,