ssh-config 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- data/MIT-LICENSE +22 -0
- data/README.rdoc +66 -0
- data/bin/ssh-config +66 -0
- data/lib/config_file.rb +126 -0
- data/lib/config_section.rb +57 -0
- data/lib/ssh-config.rb +3 -0
- metadata +73 -0
data/MIT-LICENSE
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
Copyright (c) 2008-2009 David Brady github@shinybit.com
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person
|
4
|
+
obtaining a copy of this software and associated documentation
|
5
|
+
files (the "Software"), to deal in the Software without
|
6
|
+
restriction, including without limitation the rights to use,
|
7
|
+
copy, modify, merge, publish, distribute, sublicense, and/or sell
|
8
|
+
copies of the Software, and to permit persons to whom the
|
9
|
+
Software is furnished to do so, subject to the following
|
10
|
+
conditions:
|
11
|
+
|
12
|
+
The above copyright notice and this permission notice shall be
|
13
|
+
included in all copies or substantial portions of the Software.
|
14
|
+
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
16
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
17
|
+
OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
18
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
19
|
+
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
20
|
+
WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
21
|
+
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
22
|
+
OTHER DEALINGS IN THE SOFTWARE.
|
data/README.rdoc
ADDED
@@ -0,0 +1,66 @@
|
|
1
|
+
= ssh-config: A Tool for Managing ssh Config Files
|
2
|
+
|
3
|
+
== Overview
|
4
|
+
|
5
|
+
It's not THAT much trouble to update your .ssh/config file every time
|
6
|
+
a host changes, but when it starts happening often enough, even that
|
7
|
+
hassle starts to add up. This is a quick tool I wrote to help handle
|
8
|
+
them.
|
9
|
+
|
10
|
+
It takes great care to not trash your config file, so you can continue
|
11
|
+
to edit your config files by hand before and after running the tool.
|
12
|
+
|
13
|
+
ssh-config will make a backup of your ~/.ssh/config file as
|
14
|
+
~/.ssh/config~.
|
15
|
+
|
16
|
+
Probably the most useful command is "copy", which intelligently copies
|
17
|
+
an existing host section.
|
18
|
+
|
19
|
+
== Commands
|
20
|
+
|
21
|
+
=== set <host> <key> <value>
|
22
|
+
|
23
|
+
Adds or updates the value for a given host.
|
24
|
+
|
25
|
+
=== unset <host> <key>
|
26
|
+
|
27
|
+
Removes a key value for a given host. NOTE: If all values are removed
|
28
|
+
from a section, the section is NOT removed; use rm <host> for that.
|
29
|
+
|
30
|
+
=== rm <host>
|
31
|
+
|
32
|
+
Removes an entire host section.
|
33
|
+
|
34
|
+
=== copy <old_host> <new_host>
|
35
|
+
|
36
|
+
Copies the entire section named <old_host> to a new section called
|
37
|
+
<new_host>. If old_host has a Hostname section, ssh-config will try to
|
38
|
+
update it to reflect the new_host name. For example, if you had a
|
39
|
+
section like
|
40
|
+
|
41
|
+
Host rails01
|
42
|
+
Hostname rails01.example.com
|
43
|
+
|
44
|
+
And you did ssh-config copy rails01 rails02, the new section would
|
45
|
+
look like this:
|
46
|
+
|
47
|
+
Host rails02
|
48
|
+
Hostname rails02.example.com
|
49
|
+
|
50
|
+
=== dump
|
51
|
+
|
52
|
+
Dumps the entire file.
|
53
|
+
|
54
|
+
=== show <host>
|
55
|
+
|
56
|
+
Dumps one section. (Similar to ssh-what.)
|
57
|
+
|
58
|
+
=== search <pattern>
|
59
|
+
|
60
|
+
Shows all sections that have any line (key OR value) that matches
|
61
|
+
pattern. (Similar to ssh-what.)
|
62
|
+
|
63
|
+
=== list
|
64
|
+
|
65
|
+
Lists all section names (just the Host line)
|
66
|
+
|
data/bin/ssh-config
ADDED
@@ -0,0 +1,66 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
require 'ftools'
|
3
|
+
require File.expand_path(File.join(File.dirname(__FILE__), '..', 'lib', 'ssh-config'))
|
4
|
+
|
5
|
+
# ssh-config - Manipulate config values in the .ssh/config file.
|
6
|
+
#
|
7
|
+
# ssh-config help
|
8
|
+
# ssh-config dump
|
9
|
+
# ssh-config list
|
10
|
+
# ssh-config show <host-nickname>
|
11
|
+
# ssh-config find <regex>
|
12
|
+
# ssh-config set <host-nickname> <setting> <value> [<setting> <value> [...]]
|
13
|
+
# Note: "<setting> -" deletes a setting
|
14
|
+
# ssh-config rm <host-nickname> # delete config settings for that host
|
15
|
+
# ssh-config copy <host-nickname> <new-host-nickname> # copy settings from one to the other.
|
16
|
+
|
17
|
+
config = ConfigFile.new
|
18
|
+
argv = ARGV
|
19
|
+
command = argv.shift
|
20
|
+
|
21
|
+
def usage
|
22
|
+
str =<<HELP
|
23
|
+
ssh-config - Configure your .ssh/config file
|
24
|
+
|
25
|
+
Usage:
|
26
|
+
ssh-config <command> <params>
|
27
|
+
|
28
|
+
Commands:
|
29
|
+
help - show this message
|
30
|
+
dump - parse and dump the config file
|
31
|
+
list - list configured hosts
|
32
|
+
show <host> - display the settings for host
|
33
|
+
find <pattern> - find all hosts with any detail matching pattern
|
34
|
+
set <host> <setting> <value> [<setting> <value> [...]] - set a value
|
35
|
+
NOTE: If host does not exist, it will be created
|
36
|
+
NOTE: If value is -, setting will be deleted, e.g. set User -
|
37
|
+
NOTE: If all values are deleted, section will NOT be removed, use rm instead
|
38
|
+
unset <host> <setting> - Remove a setting from a host section
|
39
|
+
rm <host> - Remove configuration for a host
|
40
|
+
copy <host> <newhost> - Duplicate the settings for a host
|
41
|
+
NOTE: If Hostname contains Host, new host will be automagically updated
|
42
|
+
HELP
|
43
|
+
|
44
|
+
end
|
45
|
+
|
46
|
+
case command
|
47
|
+
when 'help'
|
48
|
+
puts usage
|
49
|
+
when 'list'
|
50
|
+
puts config.list
|
51
|
+
when 'show'
|
52
|
+
puts config.show(argv.shift)
|
53
|
+
when 'search'
|
54
|
+
puts config.search(argv.shift)
|
55
|
+
when 'cp', 'copy'
|
56
|
+
config.copy! argv.shift, argv.shift
|
57
|
+
when 'unset'
|
58
|
+
config.unset!(argv.shift, *argv)
|
59
|
+
when 'set'
|
60
|
+
config.set!(*argv)
|
61
|
+
when 'rm', 'del', 'delete'
|
62
|
+
config.rm! argv.shift
|
63
|
+
when 'dump'
|
64
|
+
puts config.dump
|
65
|
+
end
|
66
|
+
|
data/lib/config_file.rb
ADDED
@@ -0,0 +1,126 @@
|
|
1
|
+
class ConfigFile
|
2
|
+
def initialize
|
3
|
+
@make_backups = true
|
4
|
+
@header_lines = []
|
5
|
+
@sections = []
|
6
|
+
@sections_by_name = {}
|
7
|
+
read_config
|
8
|
+
end
|
9
|
+
|
10
|
+
def add_section(name)
|
11
|
+
section = ConfigSection.new(name)
|
12
|
+
@sections << section
|
13
|
+
@sections_by_name[name] = section
|
14
|
+
section
|
15
|
+
end
|
16
|
+
|
17
|
+
def read_config
|
18
|
+
current_section = nil
|
19
|
+
IO.readlines(File.expand_path("~/.ssh/config")).each_with_index do |line, i|
|
20
|
+
line.rstrip!
|
21
|
+
if line =~ /\bHost\s+(.+)/
|
22
|
+
current_section = add_section($1)
|
23
|
+
else
|
24
|
+
if current_section
|
25
|
+
current_section.lines << line
|
26
|
+
else
|
27
|
+
@header_lines << line
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def show(host_nick)
|
34
|
+
@sections_by_name[host_nick]
|
35
|
+
end
|
36
|
+
|
37
|
+
def list()
|
38
|
+
to_text(@sections_by_name.keys.sort.map {|name| "Host #{name}"})
|
39
|
+
end
|
40
|
+
|
41
|
+
def search(text)
|
42
|
+
to_text(@sections.find_all {|section| section.matches?(text)}.sort_by {|section| section.name})
|
43
|
+
end
|
44
|
+
|
45
|
+
def set!(host_nick, *args)
|
46
|
+
backup if @make_backups
|
47
|
+
while args.length > 0
|
48
|
+
key, value = args.shift, args.shift
|
49
|
+
section = set(host_nick, key, value)
|
50
|
+
end
|
51
|
+
save
|
52
|
+
section
|
53
|
+
end
|
54
|
+
|
55
|
+
def set(host_nick, key, value)
|
56
|
+
section = @sections_by_name[host_nick] || add_section(host_nick)
|
57
|
+
section[key] = value
|
58
|
+
end
|
59
|
+
|
60
|
+
def unset!(host_nick, *keys)
|
61
|
+
backup if @make_backups
|
62
|
+
while keys.length > 0
|
63
|
+
section = unset(host_nick, keys.shift)
|
64
|
+
end
|
65
|
+
save
|
66
|
+
section
|
67
|
+
end
|
68
|
+
|
69
|
+
def unset(host_nick, key)
|
70
|
+
if section = @sections_by_name[host_nick]
|
71
|
+
section.unset(key)
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
def dump
|
76
|
+
to_text([@header_lines, @sections].flatten)
|
77
|
+
end
|
78
|
+
|
79
|
+
def rm!(host_nick)
|
80
|
+
backup if @make_backups
|
81
|
+
rm(host_nick)
|
82
|
+
save
|
83
|
+
end
|
84
|
+
|
85
|
+
def rm(host_nick)
|
86
|
+
if @sections_by_name.key?(host_nick)
|
87
|
+
@sections_by_name.delete host_nick
|
88
|
+
@sections.delete_at(@sections.index{|s| s.name == host_nick})
|
89
|
+
end
|
90
|
+
end
|
91
|
+
|
92
|
+
def copy!(old_host_nick, new_host_nick)
|
93
|
+
backup if @make_backups
|
94
|
+
copy(old_host_nick, new_host_nick)
|
95
|
+
save
|
96
|
+
end
|
97
|
+
|
98
|
+
def copy(old_host_nick, new_host_nick)
|
99
|
+
if @sections_by_name.key?(old_host_nick)
|
100
|
+
old_section = @sections_by_name[old_host_nick]
|
101
|
+
new_section = @sections_by_name[new_host_nick] || add_section(new_host_nick)
|
102
|
+
new_section.lines = old_section.lines.dup
|
103
|
+
|
104
|
+
if old_section["Hostname"]
|
105
|
+
new_section["Hostname"] = old_section["Hostname"].gsub(old_host_nick, new_host_nick)
|
106
|
+
end
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
def save
|
111
|
+
File.open(File.expand_path("~/.ssh/config"), "w") do |file|
|
112
|
+
file.puts dump
|
113
|
+
end
|
114
|
+
end
|
115
|
+
|
116
|
+
def backup
|
117
|
+
File.copy(File.expand_path("~/.ssh/config"), File.expand_path("~/.ssh/config~"))
|
118
|
+
end
|
119
|
+
|
120
|
+
private
|
121
|
+
|
122
|
+
def to_text(ray)
|
123
|
+
ray.map {|s| s.to_s } * "\n"
|
124
|
+
end
|
125
|
+
end
|
126
|
+
|
@@ -0,0 +1,57 @@
|
|
1
|
+
class ConfigSection
|
2
|
+
attr_accessor :name, :lines, :settings
|
3
|
+
|
4
|
+
def initialize(name)
|
5
|
+
@name = name
|
6
|
+
@settings = {}
|
7
|
+
@lines = []
|
8
|
+
end
|
9
|
+
|
10
|
+
def [](setting)
|
11
|
+
unless @settings.key? setting
|
12
|
+
if line = lines[setting_index(setting)]
|
13
|
+
key,val = line.split(nil, 2)
|
14
|
+
@settings[key] = val
|
15
|
+
end
|
16
|
+
end
|
17
|
+
@settings[setting]
|
18
|
+
end
|
19
|
+
|
20
|
+
def unset(setting)
|
21
|
+
if line_num = setting_index(setting)
|
22
|
+
@settings.delete setting
|
23
|
+
@lines.delete_at line_num
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
def to_s
|
28
|
+
["Host #{name}", *lines] * "\n"
|
29
|
+
end
|
30
|
+
|
31
|
+
def []=(setting, value)
|
32
|
+
if value != '-'
|
33
|
+
line_num = setting_index(setting) || lines.length
|
34
|
+
lines[line_num] = format_line(setting, value)
|
35
|
+
else
|
36
|
+
@settings.delete(setting)
|
37
|
+
@lines.delete_at(setting_index(setting))
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
def matches?(text)
|
42
|
+
r = Regexp.new text
|
43
|
+
name =~ r || lines.any? {|line| line =~ r}
|
44
|
+
end
|
45
|
+
|
46
|
+
protected
|
47
|
+
|
48
|
+
def format_line(setting, value)
|
49
|
+
" #{setting} #{value}"
|
50
|
+
end
|
51
|
+
|
52
|
+
def setting_index(setting)
|
53
|
+
r = Regexp.new(setting)
|
54
|
+
lines.index {|line| line =~ r}
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
data/lib/ssh-config.rb
ADDED
metadata
ADDED
@@ -0,0 +1,73 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: ssh-config
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
prerelease: false
|
5
|
+
segments:
|
6
|
+
- 0
|
7
|
+
- 1
|
8
|
+
- 0
|
9
|
+
version: 0.1.0
|
10
|
+
platform: ruby
|
11
|
+
authors:
|
12
|
+
- David Brady
|
13
|
+
autorequire:
|
14
|
+
bindir: bin
|
15
|
+
cert_chain: []
|
16
|
+
|
17
|
+
date: 2010-03-26 00:00:00 -06:00
|
18
|
+
default_executable:
|
19
|
+
dependencies: []
|
20
|
+
|
21
|
+
description: Ssh-Config, a tool that lets you quickly add, update, remove, and copy ssh config file entries.
|
22
|
+
email: github@shinybit.com
|
23
|
+
executables:
|
24
|
+
- ssh-config
|
25
|
+
extensions: []
|
26
|
+
|
27
|
+
extra_rdoc_files:
|
28
|
+
- README.rdoc
|
29
|
+
- MIT-LICENSE
|
30
|
+
files:
|
31
|
+
- bin/ssh-config
|
32
|
+
- lib/config_file.rb
|
33
|
+
- lib/config_section.rb
|
34
|
+
- lib/ssh-config.rb
|
35
|
+
- README.rdoc
|
36
|
+
- MIT-LICENSE
|
37
|
+
has_rdoc: true
|
38
|
+
homepage: http://github.com/dbrady/ssh-config/
|
39
|
+
licenses: []
|
40
|
+
|
41
|
+
post_install_message:
|
42
|
+
rdoc_options:
|
43
|
+
- --line-numbers
|
44
|
+
- --inline-source
|
45
|
+
- --main
|
46
|
+
- README.rdoc
|
47
|
+
- --title
|
48
|
+
- Ssh-Config - A Tool for ssh config files
|
49
|
+
require_paths:
|
50
|
+
- lib
|
51
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
52
|
+
requirements:
|
53
|
+
- - ">="
|
54
|
+
- !ruby/object:Gem::Version
|
55
|
+
segments:
|
56
|
+
- 0
|
57
|
+
version: "0"
|
58
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
59
|
+
requirements:
|
60
|
+
- - ">="
|
61
|
+
- !ruby/object:Gem::Version
|
62
|
+
segments:
|
63
|
+
- 0
|
64
|
+
version: "0"
|
65
|
+
requirements: []
|
66
|
+
|
67
|
+
rubyforge_project:
|
68
|
+
rubygems_version: 1.3.6
|
69
|
+
signing_key:
|
70
|
+
specification_version: 3
|
71
|
+
summary: Ssh-Config - tool for managing your .ssh/config file
|
72
|
+
test_files: []
|
73
|
+
|