-
Notifications
You must be signed in to change notification settings - Fork 6
Expand file tree
/
Copy pathDebian-CLI-Tool_Installer.py
More file actions
218 lines (188 loc) · 7.37 KB
/
Copy pathDebian-CLI-Tool_Installer.py
File metadata and controls
218 lines (188 loc) · 7.37 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
#!/usr/bin/env python3
import subprocess
import os
import sys
import uuid
import shutil
from shutil import which
# Why do this in python instead of
# bash? I don't use bash, second of all
# eventually I want to make this cross
# platform, and why not?
# Basically a learning tool
# Tha vast majority of this
# Can be solved by a xargs call
# to a flat file list of apps, and a check if
# apt doesn't have it, try eget
file_pass = 'a'
# Verify Debian-based system via apt-get presence
is_debian = which("apt-get")
if is_debian:
pass
else:
sys.exit("This script requires a Debian-like system such as Ubuntu, Debian or Linux Mint")
#Ask if you want to install these files, if not quit the program
file_start = input("""\nDo you want to install the below files?:\n
>> chkservice - TUI systemd unit manager
>> htop - TUI top clone on steroids
>> nnn - TUI file explorer
>> ncdu - TUI du clone, easily find what is taking up space
>> network-manager - Installs nmtui, a way to manage wireless network connections
>> ne - Nano clone, with some nice options
>> hping3 - Ping on steroids, useful on solving network issues
>> nmap - Network mapping tool, insanely powerful
>> lynis - Linux security and configuration audit tool
>> apt-show-versions - Show the versions of software installed and what needs updating
>> vim - Vi Improved, editor par exelance for Linux
>> fish - Friendly Interactive Shell - many improvements over bash
>> tig - TUI Git tool
>> bmon - Bandwith monitor
>> dnsutils - Installs dig, the DNS linux wonder-tool
>> most - pager like "less" and "more" with more options
>> eget (Github software installer)
>> lsd - ls clone that show nice icons if a nerdfont is installed
>> sd - sed clone with easier syntax
>> Lazygit - TUI git tool, works well in conjunction with tig
\n\"y\" or \"n\"?\n> """)
if file_start != 'n':
pass
else:
print("Quitting program")
sys.exit()
# Check each program in PATH; install missing ones via apt
def check_programs():
programs = ['chkservice','htop','nnn','ncdu','network-manager','ne','hping3','nmap','lynis','apt-show-versions','vim','fish','tig','bmon','dnsutils','most','curl']
os.system('sudo apt update')
for program in programs:
if which(program) is None:
print("\n>> \"" + program + '\" is not installed')
install_program(program)
else:
print("- \"" + program + '\" is installed')
# Verify package exists in apt cache before installing
def install_program(program):
try:
output = subprocess.run(["apt-cache", "search",program], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
if output.returncode == 0:
os.system("sudo apt-get install -y " + program)
print(f"{program} has been installed successfully.")
else:
print(f"{program} is not available via apt.")
except subprocess.CalledProcessError as e:
print(f"Error: {e}")
# Install eget if missing; downloads verified GitHub release (no curl|sh)
def eget_installer():
eget_exists = which("eget") is not None or os.path.exists('/usr/local/bin/eget') or os.path.exists('/usr/bin/eget')
if eget_exists:
print("- \"eget\" is installed", '\n')
return
print("Eget does not exist, installing from GitHub releases (no curl|sh)", '\n')
import platform
import tempfile
import tarfile
import json
from pathlib import Path
arch_map = {
"x86_64": "amd64", "amd64": "amd64",
"aarch64": "arm64", "arm64": "arm64",
"armv7l": "arm", "i386": "386", "i686": "386",
}
arch = arch_map.get(platform.machine().lower())
if not arch:
print(f"Unsupported architecture: {platform.machine()}")
return
api = "https://api.github.com/repos/zyedidia/eget/releases/latest"
with tempfile.TemporaryDirectory(prefix="eget-") as tmpdir:
meta_path = os.path.join(tmpdir, "release.json")
if os.system(
f'curl --fail --location --silent --show-error '
f'--connect-timeout 30 --max-time 120 -o "{meta_path}" "{api}"'
) != 0:
print("Failed to fetch eget release metadata")
return
with open(meta_path, encoding="utf-8") as handle:
release = json.load(handle)
tag = release.get("tag_name", "").lstrip("v")
asset_name = f"eget-{tag}-linux_{arch}.tar.gz"
url = next(
(a.get("browser_download_url") for a in release.get("assets", [])
if a.get("name") == asset_name),
None,
)
if not url:
print(f"No release asset {asset_name}")
return
archive = os.path.join(tmpdir, asset_name)
if os.system(
f'curl --fail --location --silent --show-error '
f'--connect-timeout 30 --max-time 120 -o "{archive}" "{url}"'
) != 0:
print("Failed to download eget archive")
return
with tarfile.open(archive, "r:gz") as tar:
member = next(
(m for m in tar.getmembers() if Path(m.name).name == "eget" and m.isfile()),
None,
)
if member is None:
print("eget binary missing from archive")
return
# Reject path traversal in older Python without tar filter=
if os.path.isabs(member.name) or ".." in Path(member.name).parts:
print("Refusing unsafe tar member")
return
try:
tar.extract(member, path=tmpdir, filter="data")
except TypeError:
tar.extract(member, path=tmpdir)
extracted = os.path.join(tmpdir, member.name)
# Basic ELF sanity check before privileged install
with open(extracted, "rb") as handle:
if handle.read(4) != b"\x7fELF":
print("Refusing to install non-ELF eget binary")
return
os.chmod(extracted, 0o755)
staged = os.path.join(os.getcwd(), "eget")
shutil.copy2(extracted, staged)
os.system(f'sudo mv "{staged}" /usr/local/bin/eget')
# Post-install validation
if which("eget") or os.path.exists("/usr/local/bin/eget"):
print("eget installed and present on PATH")
else:
print("eget install may have failed validation")
# Download binaries from GitHub releases using eget
def eget_install():
if eget_program == 'lsd':
os.system("eget lsd-rs/lsd")
elif eget_program == 'sd':
os.system("eget chmln/sd")
elif eget_program == 'lazygit':
os.system("eget jesseduffield/lazygit")
else:
print('Program not found\n')
# Move eget-downloaded binaries from current dir to PATH
def eget_copy():
for eget_program in eget_programs:
if os.path.exists(eget_program):
os.system('sudo cp '+eget_program+' /usr/bin/')
print("\nCopied \"" + eget_program + "\" to /usr/bin")
pass
else:
pass
#run eget_installer()
eget_installer()
eget_programs = ['lsd','sd','lazygit']
for eget_program in eget_programs:
if which(eget_program) is None:
print("\n>> \"" + eget_program + '\" is not installed')
eget_install(eget_program)
else:
print("- \"" + eget_program + '\" is installed')
pass
#run eget_copy()
eget_copy()
#run check_programs()
check_programs()
#Press reuturn to quit
input('\n\nPress return to quit')
sys.exit()