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

Files changed (72) hide show
  1. machineconfig/__init__.py +4 -2
  2. machineconfig/jobs/python/check_installations.py +38 -32
  3. machineconfig/jobs/python/create_bootable_media.py +4 -4
  4. machineconfig/jobs/python/create_zellij_template.py +3 -2
  5. machineconfig/jobs/python/python_cargo_build_share.py +14 -9
  6. machineconfig/jobs/python/python_ve_symlink.py +6 -6
  7. machineconfig/jobs/python_custom_installers/azuredatastudio.py +36 -0
  8. machineconfig/jobs/python_custom_installers/bypass_paywall.py +30 -0
  9. machineconfig/jobs/{python_linux_installers/dev → python_custom_installers}/docker_desktop.py +15 -4
  10. machineconfig/jobs/python_custom_installers/gh.py +53 -0
  11. machineconfig/jobs/python_custom_installers/goes.py +35 -0
  12. machineconfig/jobs/python_custom_installers/helix.py +43 -0
  13. machineconfig/jobs/python_custom_installers/lvim.py +48 -0
  14. machineconfig/jobs/python_custom_installers/ngrok.py +39 -0
  15. machineconfig/jobs/python_custom_installers/nvim.py +48 -0
  16. machineconfig/jobs/python_custom_installers/vscode.py +45 -0
  17. machineconfig/jobs/python_custom_installers/wezterm.py +41 -0
  18. machineconfig/profile/create.py +12 -7
  19. machineconfig/profile/shell.py +15 -13
  20. machineconfig/scripts/python/choose_wezterm_theme.py +96 -0
  21. machineconfig/scripts/python/cloud_copy.py +18 -13
  22. machineconfig/scripts/python/cloud_mount.py +41 -15
  23. machineconfig/scripts/python/cloud_repo_sync.py +57 -31
  24. machineconfig/scripts/python/cloud_sync.py +13 -15
  25. machineconfig/scripts/python/croshell.py +19 -10
  26. machineconfig/scripts/python/devops.py +22 -6
  27. machineconfig/scripts/python/devops_add_identity.py +7 -6
  28. machineconfig/scripts/python/devops_add_ssh_key.py +10 -9
  29. machineconfig/scripts/python/devops_backup_retrieve.py +5 -5
  30. machineconfig/scripts/python/devops_devapps_install.py +24 -19
  31. machineconfig/scripts/python/devops_update_repos.py +5 -4
  32. machineconfig/scripts/python/dotfile.py +8 -4
  33. machineconfig/scripts/python/fire_jobs.py +165 -55
  34. machineconfig/scripts/python/ftpx.py +18 -8
  35. machineconfig/scripts/python/mount_nfs.py +13 -10
  36. machineconfig/scripts/python/mount_nw_drive.py +4 -3
  37. machineconfig/scripts/python/mount_ssh.py +8 -5
  38. machineconfig/scripts/python/repos.py +26 -21
  39. machineconfig/scripts/python/snapshot.py +2 -2
  40. machineconfig/scripts/python/start_slidev.py +104 -0
  41. machineconfig/scripts/python/start_terminals.py +1 -1
  42. machineconfig/setup_windows/wt_and_pwsh/set_pwsh_theme.py +20 -34
  43. machineconfig/setup_windows/wt_and_pwsh/set_wt_settings.py +11 -12
  44. machineconfig/utils/installer.py +177 -217
  45. machineconfig/utils/scheduling.py +1 -1
  46. machineconfig/utils/utils.py +107 -54
  47. machineconfig/utils/ve.py +120 -16
  48. machineconfig-1.9.dist-info/LICENSE +201 -0
  49. {machineconfig-1.7.dist-info → machineconfig-1.9.dist-info}/METADATA +155 -140
  50. machineconfig-1.9.dist-info/RECORD +76 -0
  51. {machineconfig-1.7.dist-info → machineconfig-1.9.dist-info}/WHEEL +1 -1
  52. machineconfig/jobs/python_generic_installers/archive/gopass.py +0 -18
  53. machineconfig/jobs/python_generic_installers/archive/nvim.py +0 -20
  54. machineconfig/jobs/python_generic_installers/archive/opencommit.py +0 -25
  55. machineconfig/jobs/python_generic_installers/archive/strongbox.py +0 -33
  56. machineconfig/jobs/python_generic_installers/dev/__init__.py +0 -0
  57. machineconfig/jobs/python_linux_installers/archive/__init__.py +0 -0
  58. machineconfig/jobs/python_linux_installers/archive/bandwhich.py +0 -14
  59. machineconfig/jobs/python_linux_installers/archive/ranger.py +0 -19
  60. machineconfig/jobs/python_linux_installers/dev/azure_data_studio.py +0 -21
  61. machineconfig/jobs/python_linux_installers/dev/bytehound.py +0 -20
  62. machineconfig/jobs/python_linux_installers/dev/nnn.py +0 -22
  63. machineconfig/jobs/python_windows_installers/archive/ntop.py +0 -21
  64. machineconfig/jobs/python_windows_installers/dev/bypass_paywall.py +0 -22
  65. machineconfig/jobs/python_windows_installers/dev/obs_background_removal_plugin.py +0 -22
  66. machineconfig/scripts/python/choose_ohmybash_theme.py +0 -31
  67. machineconfig/scripts/python/choose_ohmyposh_theme.py +0 -57
  68. machineconfig/utils/pandas_type.py +0 -37
  69. machineconfig/utils/to_exe.py +0 -7
  70. machineconfig-1.7.dist-info/RECORD +0 -81
  71. /machineconfig/jobs/{python_generic_installers/archive → python_custom_installers}/__init__.py +0 -0
  72. {machineconfig-1.7.dist-info → machineconfig-1.9.dist-info}/top_level.txt +0 -0
@@ -1,8 +1,11 @@
1
1
 
2
2
  """utils"""
3
3
 
4
- import crocodile.toolbox as tb
4
+
5
5
  from machineconfig.utils.utils import CONFIG_PATH, DEFAULTS_PATH, write_shell_script, get_shell_file_executing_python_script
6
+ from crocodile.file_management import P, Read, install_n_import
7
+ from crocodile.core import randstr
8
+ from crocodile.meta import Terminal
6
9
  import argparse
7
10
  import platform
8
11
  from typing import Optional
@@ -10,10 +13,24 @@ from typing import Optional
10
13
  # import subprocess
11
14
 
12
15
 
13
- def get_wt_cmd(wd1: tb.P, wd2: tb.P) -> str: return f"""wt --window 0 new-tab --profile pwsh --title "gitdiff" --tabColor `#3b04d1 --startingDirectory {wd1} ` --colorScheme "Solarized Dark" `; split-pane --horizontal --profile pwsh --startingDirectory {wd2} --size 0.5 --colorScheme "Tango Dark" -- pwsh -Interactive"""
16
+ def get_wt_cmd(wd1: P, wd2: P) -> str:
17
+ lines = [
18
+ f"""wt --window 0 new-tab --profile pwsh --title "gitdiff" --tabColor `#3b04d1 --startingDirectory {wd1} ` --colorScheme "Solarized Dark" """,
19
+ f"""split-pane --horizontal --profile pwsh --startingDirectory {wd2} --size 0.5 --colorScheme "Tango Dark" -- pwsh -Interactive """
20
+ ]
21
+ return " `; ".join(lines)
14
22
 
15
23
 
16
- def get_zellij_cmd(wd1: tb.P, wd2: tb.P) -> str: return f""" zellij action new-tab --name gitdiff; zellij action new-pane --direction down --name local --cwd ./data; zellij action write-chars "cd '{wd1}'; git status"; zellij action move-focus up; zellij action close-pane; zellij action new-pane --direction down --name remote --cwd code; zellij action write-chars "cd '{wd2}'; git status" """
24
+ def get_zellij_cmd(wd1: P, wd2: P) -> str:
25
+ lines = [f""" zellij action new-tab --name gitdiff""",
26
+ f"""zellij action new-pane --direction down --name local --cwd ./data """,
27
+ f"""zellij action write-chars "cd '{wd1}'; git status" """,
28
+ f"""zellij action move-focus up; zellij action close-pane """,
29
+ f"""zellij action new-pane --direction down --name remote --cwd code """,
30
+ f"""zellij action write-chars "cd '{wd2}' """,
31
+ f"""git status" """
32
+ ]
33
+ return "; ".join(lines)
17
34
 
18
35
 
19
36
  def args_parser():
@@ -25,7 +42,7 @@ def args_parser():
25
42
  # parser.add_argument("--share", help="Repository path, defaults to cwd.", action="store_true", default=False)
26
43
 
27
44
  parser.add_argument("--cloud", "-c", help="rclone cloud profile name.", default=None)
28
- parser.add_argument("--message", "-m", help="Commit Message", default=f"new message {tb.randstr()}")
45
+ parser.add_argument("--message", "-m", help="Commit Message", default=f"new message {randstr()}")
29
46
  parser.add_argument("--skip_confirmation", "-s", help="Skip confirmation.", action="store_true", default=False)
30
47
  # parser.add_argument("--key", "-k", help="Key for encryption", default=None)
31
48
  parser.add_argument("--pwd", "-p", help="Password for encryption", default=None)
@@ -41,89 +58,98 @@ def args_parser():
41
58
 
42
59
  def main(cloud: Optional[str] = None, path: Optional[str] = None, message: Optional[str] = None, skip_confirmation: bool = False, pwd: Optional[str] = None, push: bool = True):
43
60
  if cloud is None:
44
- try: cloud_resolved = tb.Read.ini(DEFAULTS_PATH)['general']['rclone_config_name']
61
+ try:
62
+ cloud_resolved = Read.ini(DEFAULTS_PATH)['general']['rclone_config_name']
63
+ print(f"⚠️ Using default cloud: `{cloud_resolved}` from {DEFAULTS_PATH} ⚠️")
45
64
  except FileNotFoundError:
46
65
  print(f"No cloud profile found @ {DEFAULTS_PATH}, please set one up or provide one via the --cloud flag.")
47
66
  return ""
48
67
  else: cloud_resolved = cloud
49
- # repo_root = tb.P(args.repo).expanduser().absolute()
50
- repo_root = tb.P.cwd() if path is None else tb.P(path).expanduser().absolute()
51
- repo_obj = tb.install_n_import("git", "gitpython").Repo(repo_root, search_parent_directories=True)
52
- repo_root = tb.P(repo_obj.working_dir) # cwd might have been in a sub directory of repo_root, so its better to redefine it.
68
+ # repo_root = P(args.repo).expanduser().absolute()
69
+ repo_local_root = P.cwd() if path is None else P(path).expanduser().absolute()
70
+ repo_local_obj = install_n_import("git", "gitpython").Repo(repo_local_root, search_parent_directories=True)
71
+ repo_local_root = P(repo_local_obj.working_dir) # cwd might have been in a sub directory of repo_root, so its better to redefine it.
53
72
  CONFIG_PATH.joinpath("remote").create()
54
- repo_sync_root = CONFIG_PATH.joinpath("remote", repo_root.rel2home()) # .delete(sure=True)
73
+ repo_remote_root = CONFIG_PATH.joinpath("remote", repo_local_root.rel2home()) # .delete(sure=True)
55
74
  try:
56
75
  print("\n", "=============================== Downloading Remote Repo ====================================")
57
- remote_path = repo_root.get_remote_path(rel2home=True, os_specific=False, root="myhome") + ".zip.enc"
58
- repo_sync_root.from_cloud(remotepath=remote_path, cloud=cloud_resolved, unzip=True, decrypt=True, rel2home=True, os_specific=False, pwd=pwd)
76
+ remote_path = repo_local_root.get_remote_path(rel2home=True, os_specific=False, root="myhome") + ".zip.enc"
77
+ repo_remote_root.from_cloud(remotepath=remote_path, cloud=cloud_resolved, unzip=True, decrypt=True, rel2home=True, os_specific=False, pwd=pwd)
59
78
  except AssertionError:
60
79
  print("Remote does not exist, creating it and exiting ... ")
61
- repo_root.to_cloud(cloud=cloud_resolved, zip=True, encrypt=True, rel2home=True, pwd=pwd, os_specific=False)
80
+ repo_local_root.to_cloud(cloud=cloud_resolved, zip=True, encrypt=True, rel2home=True, pwd=pwd, os_specific=False)
62
81
  return ""
63
- repo_sync_obj = tb.install_n_import("git", "gitpython").Repo(repo_sync_root)
64
- if repo_sync_obj.is_dirty():
65
- print("=" * 50, '\n', f"WRANING: the remote `{repo_sync_root}` is dirty, please commit or stash changes before proceeding.", '\n', "=" * 50)
82
+ repo_remote_obj = install_n_import("git", "gitpython").Repo(repo_remote_root)
83
+ if repo_remote_obj.is_dirty():
84
+ print("=" * 50, '\n', f"WRANING: the remote `{repo_remote_root}` is dirty, please commit or stash changes before proceeding.", '\n', "=" * 50)
66
85
 
67
86
  script = f"""
68
87
  echo ""
69
88
  echo "=============================== Committing Local Changes ==================================="
70
- cd {repo_root}
89
+ cd {repo_local_root}
71
90
  git status
72
91
  git add .
73
92
  git commit -am "{message}"
74
93
  echo ""
75
94
  echo ""
76
95
  echo "=============================== Pulling Latest From Remote ================================"
77
- cd {repo_root}
96
+ cd {repo_local_root}
78
97
  echo '-> Trying to removing originEnc remote from local repo if it exists.'
79
98
  git remote remove originEnc
80
99
  echo '-> Adding originEnc remote to local repo'
81
- git remote add originEnc {repo_sync_root}
100
+ git remote add originEnc {repo_remote_root}
82
101
  echo '-> Fetching originEnc remote.'
83
102
  git pull originEnc master
84
103
 
85
104
  """
86
105
  suffix = '.ps1' if platform.system() == 'Windows' else '.sh'
87
- res = tb.Terminal().run(f". {tb.P.tmpfile(suffix=suffix).write_text(script)}", shell="powershell").capture().print()
106
+ res = Terminal().run(f". {P.tmpfile(suffix=suffix).write_text(script)}", shell="powershell").capture().print()
88
107
 
89
108
  if res.is_successful(strict_err=True, strict_returcode=True):
90
109
  print("\n", "Pull succeeded, removing originEnc, the local copy of remote & pushing merged repo_root to remote ... ")
91
- repo_sync_root.delete(sure=True)
110
+ repo_remote_root.delete(sure=True)
92
111
  from git.remote import Remote
93
- Remote.remove(repo_obj, "originEnc")
112
+ Remote.remove(repo_local_obj, "originEnc")
94
113
  if push:
95
- repo_root.to_cloud(cloud=cloud_resolved, zip=True, encrypt=True, rel2home=True, pwd=pwd, os_specific=False)
114
+ repo_local_root.to_cloud(cloud=cloud_resolved, zip=True, encrypt=True, rel2home=True, pwd=pwd, os_specific=False)
96
115
  else:
97
- print(f"Failed to pull, keeping local copy of remote at {repo_sync_root} ... ")
116
+ print(f"Failed to pull, keeping local copy of remote at {repo_remote_root} ... ")
98
117
 
99
118
  if push:
100
119
  if skip_confirmation: resp = "y"
101
- else: resp = input(f"Would you like to proceed syncing `{repo_root}` to `{cloud_resolved}` by pushing local changes to remote and deleting local copy of remote? y/[n] ") or "n"
120
+ else: resp = input(f"Would you like to proceed syncing `{repo_local_root}` to `{cloud_resolved}` by pushing local changes to remote and deleting local copy of remote? y/[n] ") or "n"
102
121
  else: resp = "n"
103
122
 
104
123
  if resp.lower() == "y":
105
- delete_remote_repo_copy_and_push_local(remote_repo=repo_sync_root.str, local_repo=repo_root.str, cloud=cloud_resolved)
124
+ delete_remote_repo_copy_and_push_local(remote_repo=repo_remote_root.str, local_repo=repo_local_root.str, cloud=cloud_resolved)
106
125
  else:
107
126
  program = f"""
108
127
  from machineconfig.scripts.python.cloud_repo_sync import delete_remote_repo_copy_and_push_local as func
109
- func(remote_repo=r'{repo_sync_root.str}', local_repo=r'{repo_root.str}', cloud=r'{cloud_resolved}')
128
+ func(remote_repo=r'{repo_remote_root.str}', local_repo=r'{repo_local_root.str}', cloud=r'{cloud_resolved}')
110
129
  """
111
130
  shell_file = get_shell_file_executing_python_script(python_script=program)
112
131
  print(f"When ready, use this snippet: \n. {shell_file}")
132
+ print(f"""
133
+ Or, if you want to delete local repo and replace with remote, run the following bash commands:
134
+
135
+ rm -rfd {repo_local_root}
136
+ mv {repo_remote_root} {repo_local_root}
137
+
138
+ """)
113
139
  if platform.system() == "Windows":
114
- program = get_wt_cmd(wd1=repo_root, wd2=repo_sync_root)
140
+ program = get_wt_cmd(wd1=repo_local_root, wd2=repo_remote_root)
115
141
  write_shell_script(program=program, execute=True)
116
142
  return None
117
143
  elif platform.system() == "Linux":
118
- program = get_zellij_cmd(wd1=repo_root, wd2=repo_sync_root)
144
+ program = get_zellij_cmd(wd1=repo_local_root, wd2=repo_remote_root)
119
145
  write_shell_script(program=program, execute=True)
120
146
  return None
121
147
  else: raise NotImplementedError(f"Platform {platform.system()} not implemented.")
122
148
 
123
149
 
124
150
  def delete_remote_repo_copy_and_push_local(remote_repo: str, local_repo: str, cloud: str):
125
- repo_sync_root = tb.P(remote_repo).expanduser().absolute()
126
- repo_root_path = tb.P(local_repo).expanduser().absolute()
151
+ repo_sync_root = P(remote_repo).expanduser().absolute()
152
+ repo_root_path = P(local_repo).expanduser().absolute()
127
153
  repo_sync_root.delete(sure=True)
128
154
  from git.remote import Remote
129
155
  from git.repo import Repo
@@ -5,14 +5,17 @@ TODO: use typer to make clis
5
5
  """
6
6
 
7
7
  from crocodile.file_management import P, Read, Struct
8
- from crocodile.core import install_n_import
8
+ # from crocodile.core import install_n_import
9
9
  from machineconfig.utils.utils import PROGRAM_PATH, DEFAULTS_PATH
10
10
  from machineconfig.scripts.python.cloud_mount import get_mprocs_mount_txt
11
11
  import argparse
12
12
  import os
13
13
  from typing import Optional
14
14
  # from dataclasses import dataclass
15
+ # install_n_import("pydantic")
15
16
  # from tap import Tap
17
+ from pydantic.dataclasses import dataclass
18
+ from pydantic import ConfigDict
16
19
 
17
20
 
18
21
  ES = "^" # chosen carefully to not mean anything on any shell. `$` was a bad choice.
@@ -32,15 +35,8 @@ class ArgsDefaults:
32
35
  pwd = None
33
36
 
34
37
 
35
- install_n_import("pydantic")
36
- from pydantic.dataclasses import dataclass # type: ignore # ruffle: ignore
37
- from pydantic import ConfigDict
38
-
39
-
40
38
  @dataclass(config=ConfigDict(extra="forbid", frozen=True))
41
39
  class Args():
42
- # source: str
43
- # target: str
44
40
  cloud: Optional[str] = None
45
41
 
46
42
  zip: bool = ArgsDefaults.zip_
@@ -81,12 +77,14 @@ def get_secure_share_cloud_config(interactive: bool = True) -> Args:
81
77
  cloud = default_cloud
82
78
  else:
83
79
  try:
84
- default_cloud = Read.ini(DEFAULTS_PATH)['general']['rclone_config_name']
80
+ default_cloud__ = Read.ini(DEFAULTS_PATH)['general']['rclone_config_name']
85
81
  except Exception:
86
- default_cloud = 'No default cloud found.'
87
- if default_cloud == 'No default cloud found.' or interactive:
88
- cloud = input(f"Enter cloud name (default {default_cloud}): ") or default_cloud
89
- else: cloud = default_cloud
82
+ default_cloud__ = 'No default cloud found.'
83
+ if default_cloud__ == 'No default cloud found.' or interactive:
84
+ # assert default_cloud is not None
85
+ cloud = input(f"Enter cloud name (default {default_cloud__}): ") or default_cloud__
86
+ else:
87
+ cloud = default_cloud__
90
88
 
91
89
  default_password_path = P.home().joinpath("dotfiles/creds/passwords/quick_password")
92
90
  if default_password_path.exists():
@@ -99,7 +97,7 @@ def get_secure_share_cloud_config(interactive: bool = True) -> Args:
99
97
  res = Args(cloud=cloud,
100
98
  pwd=pwd, encrypt=True,
101
99
  zip=True, overwrite=True, share=True,
102
- rel2home=True, root="myhome", os_specific=False,)
100
+ rel2home=True, root="myshare", os_specific=False,)
103
101
  Struct(res.__dict__).print(as_config=True, title=f"⚠️ Using SecureShare cloud config")
104
102
  return res
105
103
 
@@ -215,7 +213,7 @@ def args_parser():
215
213
  parser.add_argument("--transfers", "-t", help="Number of threads in syncing.", default=10) # default is False
216
214
  parser.add_argument("--root", "-R", help="Remote root.", default="myhome") # default is False
217
215
 
218
- # parser.add_argument("--key", "-k", help="Key for encryption", default=None)
216
+ parser.add_argument("--key", "-k", help="Key for encryption", default=None)
219
217
  parser.add_argument("--pwd", "-P", help="Password for encryption", default=None)
220
218
  parser.add_argument("--encrypt", "-e", help="Decrypt after receiving.", action="store_true") # default is False
221
219
  parser.add_argument("--zip", "-z", help="unzip after receiving.", action="store_true") # default is False
@@ -8,7 +8,7 @@ import argparse
8
8
  # import subprocess
9
9
  # import platform
10
10
  from crocodile.file_management import P, randstr
11
- from machineconfig.utils.ve import get_ipython_profile, get_ve_profile
11
+ from machineconfig.utils.ve import get_ipython_profile, get_ve_profile, get_ve_name_and_ipython_profile
12
12
  from machineconfig.utils.utils import PROGRAM_PATH, display_options
13
13
 
14
14
 
@@ -34,8 +34,8 @@ def get_read_data_pycode(path: str):
34
34
  p = P(r\'{path}\').absolute()
35
35
  try:
36
36
  dat = p.readit()
37
- if type(dat) == tb.Struct: dat.print(as_config=True, title=p.name)
38
- else: print(f"Succcesfully read the file {{p.name}}")
37
+ if isinstance(dat, dict): Struct(dat).print(as_config=True, title=p.name)
38
+ else: print(f"Successfully read the file {{p.name}}")
39
39
  except Exception as e:
40
40
  print(e)
41
41
 
@@ -67,7 +67,7 @@ def build_parser():
67
67
  parser.add_argument("--fzf", "-F", help="search with fuzzy finder for python scripts and run them", action="store_true", default=False)
68
68
 
69
69
  # OPTIONAL KEYWORD
70
- parser.add_argument("--venv", "-v", help="virtual enviroment to use, defaults to activated ve, if existed, else ve.", default=None)
70
+ parser.add_argument("--ve", "-v", help="virtual enviroment to use, defaults to activated ve, if existed, else ve.", default=None)
71
71
  parser.add_argument("--profile", "-P", help="ipython profile to use, defaults to default profile.", default=None)
72
72
  parser.add_argument("--read", "-r", dest="read", help="read a binary file.", default="")
73
73
  parser.add_argument("--file", "-f", dest="file", help="python file path to interpret", default="")
@@ -93,17 +93,23 @@ def build_parser():
93
93
  options = P.cwd().search("*.py", r=True).apply(str).list
94
94
  file = display_options(msg="Choose a python file to run", options=options, fzf=True, multi=False, )
95
95
  assert isinstance(file, str)
96
- if profile is None: profile = profile = get_ipython_profile(P(file))
96
+ if profile is None:
97
+ profile = get_ipython_profile(P(file))
97
98
  program = P(file).read_text(encoding='utf-8')
98
99
 
99
100
  elif args.file != "":
100
101
  file = P(args.file.lstrip()).expanduser().absolute()
101
- if profile is None: profile = profile = get_ipython_profile(P(file))
102
+ if profile is None:
103
+ profile = get_ipython_profile(P(file))
102
104
  program = get_read_pyfile_pycode(file, as_module=args.module, cmd=args.cmd)
103
105
 
104
106
  elif args.read != "":
105
107
  file = P(str(args.read).lstrip()).expanduser().absolute()
106
- if profile is None: profile = profile = get_ipython_profile(P(file))
108
+ ve_name_from_file, ipy_profile_from_file = get_ve_name_and_ipython_profile(init_path=P(file))
109
+ # if profile is None:
110
+ # profile = get_ipython_profile(P(file))
111
+ if profile is None: profile = ipy_profile_from_file
112
+ if args.ve is None: args.ve = ve_name_from_file
107
113
  program = get_read_data_pycode(str(file))
108
114
 
109
115
  else: # just run croshell.py interactively
@@ -129,9 +135,11 @@ print_logo(logo="crocodile")
129
135
  total_program = preprogram + add_print_header_pycode(str(pyfile), title=title) + program
130
136
 
131
137
  pyfile.write_text(total_program, encoding='utf-8')
132
- if profile is None: profile = "default"
138
+ if profile is None:
139
+ profile = get_ipython_profile(P.cwd())
140
+ # profile = "default"
133
141
 
134
- ve = get_ve_profile(P(file)) if args.venv is None else str(args.ve)
142
+ ve = get_ve_profile(P(file)) if args.ve is None else str(args.ve)
135
143
 
136
144
  final_program = f"""
137
145
  # deactivate
@@ -140,7 +148,8 @@ print_logo(logo="crocodile")
140
148
  if interpreter == "ipython": final_program += f"{interactivity} --profile {profile} --no-banner"
141
149
  final_program += f" {str(pyfile)}"
142
150
  print(f"🔥 sourcing ... {pyfile}")
143
- PROGRAM_PATH.write_text(final_program)
151
+ # print(f"Running ... {final_program}")
152
+ PROGRAM_PATH.write_text(data=final_program)
144
153
 
145
154
  # if platform.system() == "Windows":
146
155
  # return subprocess.run([f"powershell", "-Command", res], shell=True, capture_output=False, text=True, check=True)
@@ -1,11 +1,11 @@
1
1
 
2
+
3
+
2
4
  """devops
3
5
  """
4
-
5
- from platform import system
6
- # import subprocess
7
- # import crocodile.toolbox as tb
6
+ from crocodile.file_management import P
8
7
  from machineconfig.utils.utils import display_options, PROGRAM_PATH, write_shell_script
8
+ from platform import system
9
9
  from enum import Enum
10
10
  from typing import Optional
11
11
 
@@ -48,8 +48,24 @@ def main(which: Optional[str] = None):
48
48
  program = helper.main()
49
49
 
50
50
  elif choice_key == Options.ve.value:
51
- from machineconfig.utils.ve import get_ve_install_script
52
- program = get_ve_install_script()
51
+ program = ""
52
+ reply: bool = False
53
+ if P.cwd().joinpath(".ve.ini").exists():
54
+ reply = input("Detected .ve.ini file. Do you want to use it to build ve? (y/[n]): ") == "y"
55
+ if reply:
56
+ from machineconfig.utils.ve import get_ve_install_script_from_specs
57
+ program_win = get_ve_install_script_from_specs(repo_root=P.cwd().str, system="Windows")
58
+ program_lin = get_ve_install_script_from_specs(repo_root=P.cwd().str, system="Linux")
59
+ install_reply = input("Proceed with installation? (y/[n]): ") == "y"
60
+ if not install_reply: program = ""
61
+ else:
62
+ if system() == "Windows": program = program_win
63
+ elif system() == "Linux": program = program_lin
64
+ else: raise ValueError(f"Unknown system: {system()}")
65
+
66
+ if not reply:
67
+ from machineconfig.utils.ve import get_ve_install_script
68
+ program = get_ve_install_script()
53
69
 
54
70
  elif choice_key == Options.cli_install.value:
55
71
  import machineconfig.scripts.python.devops_devapps_install as helper
@@ -2,20 +2,21 @@
2
2
  """ID
3
3
  """
4
4
 
5
- import crocodile.toolbox as tb
5
+
6
6
  # from platform import system
7
+ from crocodile.file_management import P
7
8
  from machineconfig.utils.utils import display_options
8
9
 
9
10
 
10
11
  def main():
11
- private_keys = tb.P.home().joinpath(".ssh").search("*.pub").apply(lambda x: x.with_name(x.stem)).filter(lambda x: x.exists())
12
+ private_keys = P.home().joinpath(".ssh").search("*.pub").apply(lambda x: x.with_name(x.stem)).filter(lambda x: x.exists())
12
13
  choice = display_options(msg="Path to private key to be used when ssh'ing: ", options=private_keys.apply(str).list + ["I have the path to the key file", "I want to paste the key itself"])
13
- if choice == "I have the path to the key file": path_to_key = tb.P(input("Input path here: ")).expanduser().absolute()
14
- elif choice == "I want to paste the key itself": path_to_key = tb.P.home().joinpath(f".ssh/{input('file name (default: my_pasted_key): ') or 'my_pasted_key'}").write_text(input("Paste the private key here: "))
15
- elif isinstance(choice, str): path_to_key = tb.P(choice)
14
+ if choice == "I have the path to the key file": path_to_key = P(input("Input path here: ")).expanduser().absolute()
15
+ elif choice == "I want to paste the key itself": path_to_key = P.home().joinpath(f".ssh/{input('file name (default: my_pasted_key): ') or 'my_pasted_key'}").write_text(input("Paste the private key here: "))
16
+ elif isinstance(choice, str): path_to_key = P(choice)
16
17
  else: raise NotImplementedError(f"Choice {choice} not supported")
17
18
  txt = f"IdentityFile {path_to_key.collapseuser().as_posix()}" # adds this id for all connections, no host specified.
18
- config_path = tb.P.home().joinpath(".ssh/config")
19
+ config_path = P.home().joinpath(".ssh/config")
19
20
  if config_path.exists(): config_path.modify_text(txt_search=txt, txt_alt=txt, replace_line=True, notfound_append=True, prepend=True) # note that Identity line must come on top of config file otherwise it won't work, hence `prepend=True`
20
21
  else: config_path.write_text(txt)
21
22
  program = f"echo 'Finished adding identity to ssh config file. {'*'*50} Consider reloading config file.'"
@@ -2,14 +2,15 @@
2
2
  """SSH
3
3
  """
4
4
 
5
- import crocodile.toolbox as tb
5
+
6
6
  from platform import system
7
7
  from machineconfig.utils.utils import LIBRARY_ROOT, display_options
8
+ from crocodile.file_management import P
8
9
 
9
10
 
10
- def get_add_ssh_key_script(path_to_key: tb.P):
11
- if system() == "Linux": authorized_keys = tb.P.home().joinpath(".ssh/authorized_keys")
12
- elif system() == "Windows": authorized_keys = tb.P("C:/ProgramData/ssh/administrators_authorized_keys")
11
+ def get_add_ssh_key_script(path_to_key: P):
12
+ if system() == "Linux": authorized_keys = P.home().joinpath(".ssh/authorized_keys")
13
+ elif system() == "Windows": authorized_keys = P("C:/ProgramData/ssh/administrators_authorized_keys")
13
14
  else: raise NotImplementedError
14
15
 
15
16
  if authorized_keys.exists():
@@ -35,7 +36,7 @@ def get_add_ssh_key_script(path_to_key: tb.P):
35
36
  program = f"cat {path_to_key} > ~/.ssh/authorized_keys"
36
37
  else:
37
38
  program = LIBRARY_ROOT.joinpath("setup_windows/openssh-server_add-sshkey.ps1")
38
- program = tb.P(program).expanduser().read_text().replace('$sshfile=""', f'$sshfile="{path_to_key}"')
39
+ program = P(program).expanduser().read_text().replace('$sshfile=""', f'$sshfile="{path_to_key}"')
39
40
 
40
41
  if system() == "Linux": program += f"""
41
42
 
@@ -50,17 +51,17 @@ sudo service ssh --full-restart
50
51
 
51
52
 
52
53
  def main():
53
- pub_keys = tb.P.home().joinpath(".ssh").search("*.pub")
54
+ pub_keys = P.home().joinpath(".ssh").search("*.pub")
54
55
  all_keys_option = f"all pub keys available ({len(pub_keys)})"
55
56
  i_have_path_option = "I have the path to the key file"
56
57
  i_paste_option = "I want to paste the key itself"
57
58
  res = display_options("Which public key to add? ", options=pub_keys.apply(str).list + [all_keys_option, i_have_path_option, i_paste_option])
58
59
  assert isinstance(res, str), f"Got {res} of type {type(res)} instead of str."
59
60
  if res == all_keys_option: program = "\n\n\n".join(pub_keys.apply(get_add_ssh_key_script))
60
- elif res == i_have_path_option: program = get_add_ssh_key_script(tb.P(input("Path: ")).expanduser().absolute())
61
- elif res == i_paste_option: program = get_add_ssh_key_script(tb.P.home().joinpath(f".ssh/{input('file name (default: my_pasted_key.pub): ') or 'my_pasted_key.pub'}").write_text(input("Paste the pub key here: ")))
61
+ elif res == i_have_path_option: program = get_add_ssh_key_script(P(input("Path: ")).expanduser().absolute())
62
+ elif res == i_paste_option: program = get_add_ssh_key_script(P.home().joinpath(f".ssh/{input('file name (default: my_pasted_key.pub): ') or 'my_pasted_key.pub'}").write_text(input("Paste the pub key here: ")))
62
63
  else:
63
- program = get_add_ssh_key_script(tb.P(res))
64
+ program = get_add_ssh_key_script(P(res))
64
65
  print(program)
65
66
  return program
66
67
 
@@ -2,11 +2,11 @@
2
2
  """BR: Backup and Retrieve
3
3
  """
4
4
 
5
- from platform import system
6
5
  # import subprocess
7
- import crocodile.toolbox as tb
6
+ from crocodile.file_management import Read, P
8
7
  from machineconfig.utils.utils import LIBRARY_ROOT, DEFAULTS_PATH, print_code, choose_cloud_interactively, display_options
9
8
  from machineconfig.scripts.python.cloud_sync import ES
9
+ from platform import system
10
10
  from typing import Any, Literal, Optional
11
11
 
12
12
 
@@ -15,7 +15,7 @@ OPTIONS = Literal["BACKUP", "RETRIEVE"]
15
15
 
16
16
  def main(direction: OPTIONS, which: Optional[str] = None):
17
17
  try:
18
- cloud: str = tb.Read.ini(DEFAULTS_PATH)['general']['rclone_config_name']
18
+ cloud: str = Read.ini(DEFAULTS_PATH)['general']['rclone_config_name']
19
19
  print(f"\n{'--' * 50}\n ⚠️ Using default cloud: `{cloud}` ⚠️\n{'--' * 50}\n")
20
20
  except (FileNotFoundError, KeyError, IndexError): cloud = choose_cloud_interactively()
21
21
 
@@ -40,8 +40,8 @@ def main(direction: OPTIONS, which: Optional[str] = None):
40
40
  flags += 'r' if item['rel2home'] == 'True' else ''
41
41
  flags += 'o' if system().lower() in item_name else ''
42
42
  if flags: flags = "-" + flags
43
- if direction == "BACKUP": program += f"""\ncloud_copy "{tb.P(item['path']).as_posix()}" $cloud {flags}\n"""
44
- elif direction == "RETRIEVE": program += f"""\ncloud_copy $cloud "{tb.P(item['path']).as_posix()}" {flags}\n"""
43
+ if direction == "BACKUP": program += f"""\ncloud_copy "{P(item['path']).as_posix()}" $cloud {flags}\n"""
44
+ elif direction == "RETRIEVE": program += f"""\ncloud_copy $cloud "{P(item['path']).as_posix()}" {flags}\n"""
45
45
  else: raise RuntimeError(f"Unknown direction: {direction}")
46
46
  if item_name == "dotfiles" and system() == "Linux": program += f"""\nchmod 700 ~/.ssh/*\n"""
47
47
  print_code(program, lexer="shell", desc=f"{direction} script")
@@ -2,11 +2,12 @@
2
2
  """Devops Devapps Install
3
3
  """
4
4
 
5
- from platform import system
6
5
  # import subprocess
7
- import crocodile.toolbox as tb
6
+ from tqdm import tqdm
7
+ from crocodile.core import List as L
8
8
  from machineconfig.utils.utils import LIBRARY_ROOT, choose_multiple_options
9
- from machineconfig.utils.installer import get_cli_py_installers_v2, Installer, install_all_v2
9
+ from machineconfig.utils.installer import get_installers, Installer, install_all
10
+ from platform import system
10
11
  from typing import Any, Optional, Literal, TypeAlias
11
12
 
12
13
 
@@ -15,11 +16,10 @@ WHICH: TypeAlias = Literal["AllEssentials", "EssentialsAndOthers", "SystemInstal
15
16
 
16
17
  def main(which: Optional[str] = None):
17
18
  sys = system()
18
- installers = get_cli_py_installers_v2(dev=False, system=sys)
19
+ installers = get_installers(dev=False, system=sys) # + get_installers(dev=True, system=sys)
19
20
  default = "AllEssentials"
20
- options = ["SystemInstallers", "OtherDevApps", "EssentialsAndOthers", "PrecheckedCloudInstaller"]
21
- options = [default] + options
22
- options = [x.get_description() for x in installers] + options
21
+ options = ["SystemInstallers", "OtherDevApps", "EssentialsAndOthers", "PrecheckedCloudInstaller", default]
22
+ options = [x.get_description() for x in tqdm(installers, desc="Checking installed programs")] + options
23
23
 
24
24
  if which is not None:
25
25
  return get_program(program_name=which, options=options, installers=list(installers))
@@ -34,14 +34,17 @@ def main(which: Optional[str] = None):
34
34
 
35
35
  def get_program(program_name: str, options: list[str], installers: list[Installer]):
36
36
  if program_name == "AllEssentials" or program_name == "EssentialsAndOthers":
37
- installers_ = get_cli_py_installers_v2(dev=False, system=system())
37
+ installers_ = get_installers(dev=False, system=system())
38
38
  if program_name == "EssentialsAndOthers":
39
- installers_ += get_cli_py_installers_v2(dev=True, system=system())
40
- install_all_v2(installers=tb.L(installers))
39
+ installers_ += get_installers(dev=True, system=system())
40
+ install_all(installers=L(installers))
41
41
  program = ""
42
42
  elif program_name == "SystemInstallers":
43
43
  if system() == "Windows": options_system = parse_apps_installer_windows(LIBRARY_ROOT.joinpath("setup_windows/apps.ps1").read_text())
44
- elif system() == "Linux": options_system = parse_apps_installer_linux(LIBRARY_ROOT.joinpath("setup_linux/apps.sh").read_text())
44
+ elif system() == "Linux":
45
+ options_system_1 = parse_apps_installer_linux(LIBRARY_ROOT.joinpath("setup_linux/apps_dev.sh").read_text())
46
+ options_system_2 = parse_apps_installer_linux(LIBRARY_ROOT.joinpath("setup_linux/apps.sh").read_text())
47
+ options_system = {**options_system_1, **options_system_2}
45
48
  else: raise NotImplementedError(f"System {system()} not supported")
46
49
  program_names = choose_multiple_options(msg="", options=sorted(list(options_system.keys())), header="CHOOSE DEV APP")
47
50
  program = ""
@@ -50,10 +53,13 @@ def get_program(program_name: str, options: list[str], installers: list[Installe
50
53
  if sub_program.startswith("#winget"): sub_program = sub_program[1:]
51
54
  program += "\n" + sub_program
52
55
  elif program_name == "OtherDevApps":
53
- installers = get_cli_py_installers_v2(dev=True, system=system())
54
- options__: list[str] = [x.get_description() for x in installers]
55
- program_names = choose_multiple_options(msg="", options=sorted(options__), header="CHOOSE DEV APP")
56
+ installers = get_installers(dev=True, system=system())
57
+ options__: list[str] = [x.get_description() for x in tqdm(installers, desc="Checking installed programs")]
58
+ program_names = choose_multiple_options(msg="", options=sorted(options__) + ["all"], header="CHOOSE DEV APP")
59
+ if "all" in program_names: program_names = options__
56
60
  program = ""
61
+ print(f"Installing:")
62
+ L(program_names).print()
57
63
  for name in program_names:
58
64
  try:
59
65
  idx = options__.index(name)
@@ -61,9 +67,8 @@ def get_program(program_name: str, options: list[str], installers: list[Installe
61
67
  print(f"{name=}")
62
68
  print(f"{options__=}")
63
69
  raise ve
70
+ print(f"Installing {name}")
64
71
  sub_program = installers[idx].install_robust(version=None) # finish the task
65
- # sub_program = "echo 'Finished Installation'" # write an empty program
66
- # program += "\n" + ""sub_program
67
72
  elif program_name == "PrecheckedCloudInstaller":
68
73
  from machineconfig.jobs.python.check_installations import PrecheckedCloudInstaller
69
74
  ci = PrecheckedCloudInstaller()
@@ -97,7 +102,7 @@ def parse_apps_installer_windows(txt: str) -> dict[str, Any]:
97
102
  if idx == 0: continue
98
103
  if idx == 1: chunks.append(item)
99
104
  else: chunks.append("winget install" + item)
100
- # progs = tb.L(txt.splitlines()).filter(lambda x: x.startswith("winget ") or x.startswith("#winget"))
105
+ # progs = L(txt.splitlines()).filter(lambda x: x.startswith("winget ") or x.startswith("#winget"))
101
106
  res: dict[str, str] = {}
102
107
  for a_chunk in chunks:
103
108
  try:
@@ -110,8 +115,8 @@ def parse_apps_installer_windows(txt: str) -> dict[str, Any]:
110
115
  except IndexError as e:
111
116
  print(a_chunk)
112
117
  raise e
113
- # tb.Struct(res).print(as_config=True)
114
- # tb.L(chunks).print(sep="-----------------------------------------------------------------------\n\n")
118
+ # Struct(res).print(as_config=True)
119
+ # L(chunks).print(sep="-----------------------------------------------------------------------\n\n")
115
120
  # import time
116
121
  # time.sleep(10)
117
122
  return res
@@ -2,9 +2,10 @@
2
2
  """Update
3
3
  """
4
4
 
5
- from platform import system
6
- import crocodile.toolbox as tb
5
+ from crocodile.file_management import P, Read
6
+ from crocodile.core import install_n_import
7
7
  from machineconfig.utils.utils import DEFAULTS_PATH
8
+ from platform import system
8
9
 
9
10
 
10
11
  sep = "\n"
@@ -14,7 +15,7 @@ def main(verbose: bool = True) -> str:
14
15
  _ = verbose
15
16
  repos: list[str] = ["~/code/crocodile", "~/code/machineconfig", ]
16
17
  try:
17
- tmp = tb.Read.ini(DEFAULTS_PATH)['general']['repos'].split(",")
18
+ tmp = Read.ini(DEFAULTS_PATH)['general']['repos'].split(",")
18
19
  if tmp[-1] == "": tmp = tmp[:-1]
19
20
  repos += tmp
20
21
  except (FileNotFoundError, KeyError, IndexError):
@@ -30,7 +31,7 @@ to_email = myemail@email.com
30
31
  repos_objs = []
31
32
  for a_package_path in repos:
32
33
  try:
33
- repo = tb.install_n_import("git", "gitpython").Repo(str(tb.P(a_package_path).expanduser()), search_parent_directories=True)
34
+ repo = install_n_import("git", "gitpython").Repo(str(P(a_package_path).expanduser()), search_parent_directories=True)
34
35
  repos_objs.append(repo)
35
36
  except Exception as ex:
36
37
  print(ex)