sshman 0.2.3 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 38a7a2d296183267a41c7ad685e108cd2c57623e97ed343e61cd74beeb3c1f44
4
- data.tar.gz: e145ddfa534871e8d7d19641f045302cd4b8011407fe2c8c304509dd1827313c
3
+ metadata.gz: b6e265f8a5efa23946251a7019e11aa20c6ae7dc8aaf743b8751dff870697e97
4
+ data.tar.gz: 5ddadf48c0474ddea5b17c9dca290dcabb20503319693e81648c27bb0600fc6f
5
5
  SHA512:
6
- metadata.gz: 0f3b7c7dc52c2acedd868abdb22b3c5fe2328d32c76acf7451849b03885ab8fa564fc794f31988c45e519c4f552e827ea2d1b83eaafb1127c0c94d306f64ade8
7
- data.tar.gz: '0887e63543c07ccb83ec4fc30c0299b38cc81104e316230efab4944ae34f3f022bf76683d8bc4fb6984995bf7959aac92fbbcc3278a9ed6d0b39cec8631731dd'
6
+ metadata.gz: 7e5fad2ae4eee2a03342fa3570efd9d63dd98515c5ba24a105f91e57d9bde7f94bab7b669ad29285ce3ae9a3f786effcdf871eb6b84facb52063c81017d619e5
7
+ data.tar.gz: 1faab44d67b2dd68fd8155bb8daee92fb8c20770cb76461cfc07e8a44bd2dbb8cf5ce2c0492686801e3cbe01a299c35e7e721cfa7c96a5efd2e7e70fb2f36019
data/lib/sshman/cli.rb ADDED
@@ -0,0 +1,98 @@
1
+ require 'logger'
2
+ require_relative 'constants'
3
+ require_relative 'version'
4
+ require_relative 'server_manager'
5
+ require_relative 'utils'
6
+
7
+ module Sshman
8
+ class CLI
9
+ LOGGER = Logger.new(File.expand_path('~/.sshman.log'))
10
+
11
+ def self.start(argv)
12
+ case argv[0]
13
+ when 'list'
14
+ new.list_servers
15
+ when 'add'
16
+ new.add_server
17
+ when 'edit'
18
+ new.edit_server
19
+ when 'delete'
20
+ new.delete_server
21
+ when 'connect'
22
+ new.connect_to_server(argv[1])
23
+ when 'help'
24
+ new.display_help
25
+ when 'version'
26
+ new.version
27
+ else
28
+ puts "Unknown command: #{argv[0]}. Use 'sshman help' for a list of commands."
29
+ end
30
+ end
31
+
32
+ def version
33
+ puts "sshman version #{Sshman::VERSION}"
34
+ end
35
+
36
+ def self.start_interactive
37
+ new.main
38
+ end
39
+
40
+ def main
41
+ ensure_csv_file
42
+
43
+ loop do
44
+ puts "\n#{YELLOW}Options:#{RESET_COLOR} list, add, edit, delete, connect, help, quit"
45
+ print "#{CYAN}Choose an option: #{RESET_COLOR}"
46
+ option = gets.chomp.downcase.strip
47
+
48
+ case option
49
+ when 'list'
50
+ list_servers
51
+ when 'add'
52
+ add_server
53
+ when 'edit'
54
+ edit_server
55
+ when 'delete'
56
+ delete_server
57
+ when 'connect'
58
+ connect_to_server
59
+ when 'help'
60
+ display_help
61
+ when 'quit'
62
+ puts "#{GREEN}Goodbye!#{RESET_COLOR}"
63
+ break
64
+ else
65
+ puts "#{RED}Unknown option '#{option}'. Type 'help' for usage instructions.#{RESET_COLOR}"
66
+ end
67
+ end
68
+ end
69
+
70
+ def ensure_csv_file
71
+ Sshman::Utils.ensure_csv_file
72
+ end
73
+
74
+ def display_help
75
+ Sshman::Utils.display_help
76
+ end
77
+
78
+ def list_servers
79
+ Sshman::ServerManager.list_servers
80
+ end
81
+
82
+ def add_server
83
+ Sshman::ServerManager.add_server
84
+ end
85
+
86
+ def edit_server
87
+ Sshman::ServerManager.edit_server
88
+ end
89
+
90
+ def delete_server
91
+ Sshman::ServerManager.delete_server
92
+ end
93
+
94
+ def connect_to_server(alias_name = nil)
95
+ Sshman::ServerManager.connect_to_server(alias_name)
96
+ end
97
+ end
98
+ end
@@ -0,0 +1,8 @@
1
+ module Sshman
2
+ RESET_COLOR = "\033[0m"
3
+ RED = "\033[31m"
4
+ GREEN = "\033[32m"
5
+ YELLOW = "\033[33m"
6
+ CYAN = "\033[36m"
7
+ SERVERS_CSV = File.expand_path("~/.sshman_servers.csv")
8
+ end
@@ -0,0 +1,131 @@
1
+ require 'csv'
2
+ require_relative 'constants'
3
+
4
+ module Sshman
5
+ class ServerManager
6
+ def self.list_servers
7
+ if File.zero?(SERVERS_CSV)
8
+ puts "#{YELLOW}No servers found. Add some using the 'add' option.#{RESET_COLOR}"
9
+ return
10
+ end
11
+
12
+ puts "#{CYAN}%-15s %-25s %-6s %-15s %-30s#{RESET_COLOR}" % ["Alias", "Hostname", "Port", "Username", "SSH Key"]
13
+ puts "-" * 95
14
+
15
+ CSV.foreach(SERVERS_CSV, headers: true) do |row|
16
+ puts "%-15s %-25s %-6s %-15s %-30s" % [row['alias'], row['hostname'], row['port'], row['username'], row['ssh_key']]
17
+ end
18
+ end
19
+
20
+ def self.add_server
21
+ puts "#{CYAN}Adding a new server...#{RESET_COLOR}"
22
+ print "Alias: "
23
+ alias_name = gets.chomp.strip
24
+ return puts "#{RED}Alias cannot be empty!#{RESET_COLOR}" if alias_name.empty?
25
+
26
+ print "Hostname or IP: "
27
+ hostname = gets.chomp.strip
28
+ return puts "#{RED}Hostname cannot be empty!#{RESET_COLOR}" if hostname.empty?
29
+
30
+ print "Port (default 22): "
31
+ port = gets.chomp.strip
32
+ port = '22' if port.empty?
33
+
34
+ print "Username: "
35
+ username = gets.chomp.strip
36
+ return puts "#{RED}Username cannot be empty!#{RESET_COLOR}" if username.empty?
37
+
38
+ print "Path to SSH key (leave blank if none): "
39
+ ssh_key = gets.chomp.strip
40
+
41
+ CSV.open(SERVERS_CSV, 'a+') do |csv|
42
+ csv << [alias_name, hostname, port, username, ssh_key]
43
+ end
44
+
45
+ puts "#{GREEN}Server '#{alias_name}' added successfully!#{RESET_COLOR}"
46
+ end
47
+
48
+ def self.edit_server
49
+ print "Enter alias of the server to edit: "
50
+ alias_name = gets.chomp.strip
51
+ servers = CSV.table(SERVERS_CSV)
52
+
53
+ server = servers.find { |row| row[:alias] == alias_name }
54
+ unless server
55
+ puts "#{RED}No server found with alias '#{alias_name}'.#{RESET_COLOR}"
56
+ return
57
+ end
58
+
59
+ print "New Hostname (leave blank to keep current: #{server[:hostname]}): "
60
+ new_hostname = gets.chomp.strip
61
+ server[:hostname] = new_hostname unless new_hostname.empty?
62
+
63
+ print "New Port (leave blank to keep current: #{server[:port]}): "
64
+ new_port = gets.chomp.strip
65
+ server[:port] = new_port unless new_port.empty?
66
+
67
+ print "New Username (leave blank to keep current: #{server[:username]}): "
68
+ new_username = gets.chomp.strip
69
+ server[:username] = new_username unless new_username.empty?
70
+
71
+ print "New SSH Key Path (leave blank to keep current: #{server[:ssh_key]}): "
72
+ new_ssh_key = gets.chomp.strip
73
+ server[:ssh_key] = new_ssh_key unless new_ssh_key.empty?
74
+
75
+ CSV.open(SERVERS_CSV, 'w') do |csv|
76
+ csv << servers.headers
77
+ servers.each { |row| csv << row }
78
+ end
79
+
80
+ puts "#{GREEN}Server '#{alias_name}' updated successfully!#{RESET_COLOR}"
81
+ end
82
+
83
+ def self.delete_server
84
+ print "Enter alias of the server to delete: "
85
+ alias_name = gets.chomp.strip
86
+ servers = CSV.table(SERVERS_CSV)
87
+
88
+ if servers.delete_if { |row| row[:alias] == alias_name }
89
+ CSV.open(SERVERS_CSV, 'w') do |csv|
90
+ csv << servers.headers
91
+ servers.each { |row| csv << row }
92
+ end
93
+ puts "#{GREEN}Server '#{alias_name}' deleted successfully!#{RESET_COLOR}"
94
+ else
95
+ puts "#{RED}No server found with alias '#{alias_name}'.#{RESET_COLOR}"
96
+ end
97
+ end
98
+
99
+ def self.connect_to_server(alias_name = nil)
100
+ if alias_name.nil?
101
+ print "Enter alias of the server to connect: "
102
+ alias_name = gets.chomp.strip
103
+ end
104
+
105
+ server = nil
106
+ CSV.foreach(SERVERS_CSV, headers: true) do |row|
107
+ if row['alias'] == alias_name
108
+ server = row
109
+ break
110
+ end
111
+ end
112
+
113
+ unless server
114
+ CLI::LOGGER.error("Failed connection attempt to #{alias_name}: No server found")
115
+ puts "#{RED}No server found with alias '#{alias_name}'.#{RESET_COLOR}"
116
+ return
117
+ end
118
+
119
+ ssh_command = "ssh #{server['username']}@#{server['hostname']} -p #{server['port']}"
120
+ ssh_command += " -i #{server['ssh_key']}" unless server['ssh_key'].to_s.empty?
121
+
122
+ CLI::LOGGER.info("Connecting to #{alias_name}...")
123
+
124
+ if system(ssh_command)
125
+ CLI::LOGGER.info("Successfully connected to #{alias_name}")
126
+ else
127
+ CLI::LOGGER.error("Failed to connect to #{alias_name}")
128
+ end
129
+ end
130
+ end
131
+ end
data/lib/sshman/sshman.rb CHANGED
@@ -1,230 +1,4 @@
1
- # lib/sshman/sshman.rb
2
- require 'csv'
3
- require 'io/console'
4
- require_relative 'version'
5
-
6
- module Sshman
7
- class CLI
8
- # This method handles inline commands
9
- def self.start(argv)
10
- case argv[0]
11
- when 'list'
12
- new.list_servers
13
- when 'add'
14
- new.add_server
15
- when 'edit'
16
- new.edit_server
17
- when 'delete'
18
- new.delete_server
19
- when 'connect'
20
- new.connect_to_server(argv[1])
21
- when 'help'
22
- new.display_help
23
- when 'version'
24
- new.version
25
- else
26
- puts "Unknown command: #{argv[0]}. Use 'sshman help' for a list of commands."
27
- end
28
- end
29
-
30
- # Display the current version
31
-
32
- def version
33
- puts "sshman version #{Sshman::VERSION}"
34
- end
35
-
36
- # This method starts the interactive menu (default)
37
- def self.start_interactive
38
- new.main
39
- end
40
-
41
- # Main interactive loop
42
- def main
43
- ensure_csv_file
44
-
45
- loop do
46
- puts "\n#{YELLOW}Options:#{RESET_COLOR} list, add, edit, delete, connect, help, quit"
47
- print "#{CYAN}Choose an option: #{RESET_COLOR}"
48
- option = gets.chomp.downcase.strip
49
-
50
- case option
51
- when 'list'
52
- list_servers
53
- when 'add'
54
- add_server
55
- when 'edit'
56
- edit_server
57
- when 'delete'
58
- delete_server
59
- when 'connect'
60
- connect_to_server
61
- when 'help'
62
- display_help
63
- when 'quit'
64
- puts "#{GREEN}Goodbye!#{RESET_COLOR}"
65
- break
66
- else
67
- puts "#{RED}Unknown option '#{option}'. Type 'help' for usage instructions.#{RESET_COLOR}"
68
- end
69
- end
70
- end
71
-
72
- # Ensure the CSV file exists and is secure
73
- def ensure_csv_file
74
- unless File.exist?(SERVERS_CSV)
75
- File.open(SERVERS_CSV, 'w') { |file| file.puts "alias,hostname,port,username,ssh_key" }
76
- puts "#{GREEN}Created servers file at #{SERVERS_CSV}.#{RESET_COLOR}"
77
- end
78
- File.chmod(0600, SERVERS_CSV) # Restrict file permissions for security
79
- end
80
-
81
- # Display help information
82
- def display_help
83
- puts <<-HELP
84
- Usage: sshman [COMMAND]
85
- Commands:
86
- list List all saved servers
87
- add Add a new server configuration
88
- edit Edit an existing server
89
- delete Delete a server by its alias
90
- connect Connect to a server by its alias
91
- version Display the current version
92
- help Display this help information
93
- HELP
94
- end
95
-
96
- # List all servers in a formatted table with colors
97
- def list_servers
98
- if File.zero?(SERVERS_CSV)
99
- puts "#{YELLOW}No servers found. Add some using the 'add' option.#{RESET_COLOR}"
100
- return
101
- end
102
-
103
- puts "#{CYAN}%-15s %-25s %-6s %-15s %-30s#{RESET_COLOR}" % ["Alias", "Hostname", "Port", "Username", "SSH Key"]
104
- puts "-" * 95
105
-
106
- CSV.foreach(SERVERS_CSV, headers: true) do |row|
107
- puts "%-15s %-25s %-6s %-15s %-30s" % [row['alias'], row['hostname'], row['port'], row['username'], row['ssh_key']]
108
- end
109
- end
110
-
111
- # Add a new server to the CSV file
112
- def add_server
113
- puts "#{CYAN}Adding a new server...#{RESET_COLOR}"
114
- print "Alias: "
115
- alias_name = gets.chomp.strip
116
- return puts "#{RED}Alias cannot be empty!#{RESET_COLOR}" if alias_name.empty?
117
-
118
- print "Hostname or IP: "
119
- hostname = gets.chomp.strip
120
- return puts "#{RED}Hostname cannot be empty!#{RESET_COLOR}" if hostname.empty?
121
-
122
- print "Port (default 22): "
123
- port = gets.chomp.strip
124
- port = '22' if port.empty?
125
-
126
- print "Username: "
127
- username = gets.chomp.strip
128
- return puts "#{RED}Username cannot be empty!#{RESET_COLOR}" if username.empty?
129
-
130
- print "Path to SSH key (leave blank if none): "
131
- ssh_key = gets.chomp.strip
132
-
133
- CSV.open(SERVERS_CSV, 'a+') do |csv|
134
- csv << [alias_name, hostname, port, username, ssh_key]
135
- end
136
-
137
- puts "#{GREEN}Server '#{alias_name}' added successfully!#{RESET_COLOR}"
138
- end
139
-
140
- # Edit an existing server's details
141
- def edit_server
142
- print "Enter alias of the server to edit: "
143
- alias_name = gets.chomp.strip
144
- servers = CSV.table(SERVERS_CSV)
145
-
146
- server = servers.find { |row| row[:alias] == alias_name }
147
- unless server
148
- puts "#{RED}No server found with alias '#{alias_name}'.#{RESET_COLOR}"
149
- return
150
- end
151
-
152
- print "New Hostname (leave blank to keep current: #{server[:hostname]}): "
153
- new_hostname = gets.chomp.strip
154
- server[:hostname] = new_hostname unless new_hostname.empty?
155
-
156
- print "New Port (leave blank to keep current: #{server[:port]}): "
157
- new_port = gets.chomp.strip
158
- server[:port] = new_port unless new_port.empty?
159
-
160
- print "New Username (leave blank to keep current: #{server[:username]}): "
161
- new_username = gets.chomp.strip
162
- server[:username] = new_username unless new_username.empty?
163
-
164
- print "New SSH Key Path (leave blank to keep current: #{server[:ssh_key]}): "
165
- new_ssh_key = gets.chomp.strip
166
- server[:ssh_key] = new_ssh_key unless new_ssh_key.empty?
167
-
168
- CSV.open(SERVERS_CSV, 'w') do |csv|
169
- csv << servers.headers
170
- servers.each { |row| csv << row }
171
- end
172
-
173
- puts "#{GREEN}Server '#{alias_name}' updated successfully!#{RESET_COLOR}"
174
- end
175
-
176
- # Delete a server from the CSV file
177
- def delete_server
178
- print "Enter alias of the server to delete: "
179
- alias_name = gets.chomp.strip
180
- servers = CSV.table(SERVERS_CSV)
181
-
182
- if servers.delete_if { |row| row[:alias] == alias_name }
183
- CSV.open(SERVERS_CSV, 'w') do |csv|
184
- csv << servers.headers
185
- servers.each { |row| csv << row }
186
- end
187
- puts "#{GREEN}Server '#{alias_name}' deleted successfully!#{RESET_COLOR}"
188
- else
189
- puts "#{RED}No server found with alias '#{alias_name}'.#{RESET_COLOR}"
190
- end
191
- end
192
-
193
- # Connect to a server using SSH
194
- def connect_to_server(alias_name = nil)
195
- # If no alias is provided, ask the user for one
196
- if alias_name.nil?
197
- print "Enter alias of the server to connect: "
198
- alias_name = gets.chomp.strip
199
- end
200
-
201
- # Search for the server in the CSV file
202
- server = nil
203
- CSV.foreach(SERVERS_CSV, headers: true) do |row|
204
- if row['alias'] == alias_name
205
- server = row
206
- break
207
- end
208
- end
209
-
210
- unless server
211
- puts "#{RED}No server found with alias '#{alias_name}'.#{RESET_COLOR}"
212
- return
213
- end
214
-
215
- ssh_command = "ssh #{server['username']}@#{server['hostname']} -p #{server['port']}"
216
- ssh_command += " -i #{server['ssh_key']}" unless server['ssh_key'].to_s.empty?
217
-
218
- puts "#{CYAN}Connecting to #{alias_name}...#{RESET_COLOR}"
219
- exec ssh_command
220
- end
221
-
222
- # Constants for coloring terminal output
223
- RESET_COLOR = "\033[0m"
224
- RED = "\033[31m"
225
- GREEN = "\033[32m"
226
- YELLOW = "\033[33m"
227
- CYAN = "\033[36m"
228
- SERVERS_CSV = File.expand_path("~/.sshman_servers.csv")
229
- end
230
- end
1
+ require_relative 'constants'
2
+ require_relative 'cli'
3
+ require_relative 'server_manager'
4
+ require_relative 'utils'
@@ -0,0 +1,28 @@
1
+ require 'csv'
2
+ require_relative 'constants'
3
+
4
+ module Sshman
5
+ class Utils
6
+ def self.ensure_csv_file
7
+ unless File.exist?(SERVERS_CSV)
8
+ File.open(SERVERS_CSV, 'w') { |file| file.puts "alias,hostname,port,username,ssh_key" }
9
+ puts "#{GREEN}Created servers file at #{SERVERS_CSV}.#{RESET_COLOR}"
10
+ end
11
+ File.chmod(0600, SERVERS_CSV)
12
+ end
13
+
14
+ def self.display_help
15
+ puts <<-HELP
16
+ Usage: sshman [COMMAND]
17
+ Commands:
18
+ list List all saved servers
19
+ add Add a new server configuration
20
+ edit Edit an existing server
21
+ delete Delete a server by its alias
22
+ connect Connect to a server by its alias
23
+ version Display the current version
24
+ help Display this help information
25
+ HELP
26
+ end
27
+ end
28
+ end
@@ -1,5 +1,5 @@
1
1
  # lib/sshman/version.rb
2
2
 
3
3
  module Sshman
4
- VERSION = "0.2.3"
4
+ VERSION = "0.3.0"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sshman
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.3
4
+ version: 0.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - SubnetMasked
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2024-10-03 00:00:00.000000000 Z
11
+ date: 2024-10-04 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description: A simple terminal-based SSH manager to add, list, delete, and connect
14
14
  to SSH servers.
@@ -20,7 +20,11 @@ extensions: []
20
20
  extra_rdoc_files: []
21
21
  files:
22
22
  - exe/sshman
23
+ - lib/sshman/cli.rb
24
+ - lib/sshman/constants.rb
25
+ - lib/sshman/server_manager.rb
23
26
  - lib/sshman/sshman.rb
27
+ - lib/sshman/utils.rb
24
28
  - lib/sshman/version.rb
25
29
  homepage: https://github.com/subnetmasked/sshman
26
30
  licenses: