svengali 0.2.7.2

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.
Files changed (63) hide show
  1. data/LICENSE +20 -0
  2. data/README +0 -0
  3. data/README.rdoc +17 -0
  4. data/Rakefile +47 -0
  5. data/VERSION +1 -0
  6. data/api_document020_en.pdf +0 -0
  7. data/api_document020_ja.pdf +0 -0
  8. data/api_document_en.pptx +0 -0
  9. data/api_document_ja.pptx +0 -0
  10. data/lib/svengali.rb +2 -0
  11. data/lib/svengali/config.rb +78 -0
  12. data/lib/svengali/ext_string.rb +55 -0
  13. data/lib/svengali/ext_string/command.yml +6 -0
  14. data/lib/svengali/ext_string/path.yml +6 -0
  15. data/lib/svengali/file_io.rb +106 -0
  16. data/lib/svengali/machine.rb +123 -0
  17. data/lib/svengali/platforms/debian.rb +5 -0
  18. data/lib/svengali/platforms/default.rb +4 -0
  19. data/lib/svengali/plugins/eucalyptus.rb +339 -0
  20. data/lib/svengali/plugins/machine_config.rb +126 -0
  21. data/lib/svengali/plugins/package.rb +7 -0
  22. data/lib/svengali/ssh.rb +106 -0
  23. data/lib/svengali/svengali.rb +19 -0
  24. data/lib/svengali/util.rb +117 -0
  25. data/rdoc/classes/CLibIPAddr.html +230 -0
  26. data/rdoc/classes/Cloud.html +506 -0
  27. data/rdoc/classes/Config.html +151 -0
  28. data/rdoc/classes/Config/ConfigFile.html +319 -0
  29. data/rdoc/classes/ExtStr.html +209 -0
  30. data/rdoc/classes/ExtStrAccessor.html +183 -0
  31. data/rdoc/classes/FileIO.html +415 -0
  32. data/rdoc/classes/Machine.html +771 -0
  33. data/rdoc/classes/MachineMaster.html +117 -0
  34. data/rdoc/classes/Platform.html +121 -0
  35. data/rdoc/classes/SSH.html +315 -0
  36. data/rdoc/created.rid +1 -0
  37. data/rdoc/files/README.html +101 -0
  38. data/rdoc/files/README_rdoc.html +133 -0
  39. data/rdoc/files/lib/svengali/config_rb.html +114 -0
  40. data/rdoc/files/lib/svengali/ext_string_rb.html +108 -0
  41. data/rdoc/files/lib/svengali/file_io_rb.html +115 -0
  42. data/rdoc/files/lib/svengali/machine_rb.html +108 -0
  43. data/rdoc/files/lib/svengali/platforms/debian_rb.html +107 -0
  44. data/rdoc/files/lib/svengali/platforms/default_rb.html +107 -0
  45. data/rdoc/files/lib/svengali/plugins/eucalyptus_rb.html +389 -0
  46. data/rdoc/files/lib/svengali/plugins/machine_config_rb.html +101 -0
  47. data/rdoc/files/lib/svengali/plugins/package_rb.html +101 -0
  48. data/rdoc/files/lib/svengali/ssh_rb.html +110 -0
  49. data/rdoc/files/lib/svengali/svengali_rb.html +125 -0
  50. data/rdoc/files/lib/svengali/util_rb.html +439 -0
  51. data/rdoc/files/lib/svengali_rb.html +108 -0
  52. data/rdoc/fr_class_index.html +37 -0
  53. data/rdoc/fr_file_index.html +41 -0
  54. data/rdoc/fr_method_index.html +100 -0
  55. data/rdoc/index.html +26 -0
  56. data/rdoc/rdoc-style.css +208 -0
  57. data/spec/spec.opts +1 -0
  58. data/spec/spec_helper.rb +9 -0
  59. data/spec/svengali_spec.rb +7 -0
  60. data/svengali.gemspec +113 -0
  61. data/svengali_sample.rb +43 -0
  62. data/test/scenario.sh +3 -0
  63. metadata +179 -0
data/LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2009 Ryo Kanbayashi
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README ADDED
File without changes
@@ -0,0 +1,17 @@
1
+ = svengali
2
+
3
+ Description goes here.
4
+
5
+ == Note on Patches/Pull Requests
6
+
7
+ * Fork the project.
8
+ * Make your feature addition or bug fix.
9
+ * Add tests for it. This is important so I don't break it in a
10
+ future version unintentionally.
11
+ * Commit, do not mess with rakefile, version, or history.
12
+ (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
13
+ * Send me a pull request. Bonus points for topic branches.
14
+
15
+ == Copyright
16
+
17
+ Copyright (c) 2010 Ryo Kanbayashi. See LICENSE for details.
@@ -0,0 +1,47 @@
1
+ require 'rubygems'
2
+ require 'rake'
3
+
4
+ begin
5
+ require 'jeweler'
6
+ Jeweler::Tasks.new do |gem|
7
+ gem.name = "svengali"
8
+ gem.summary = "distributed machine operating library of cloud age. please see http://sourceforge.jp/projects/svengali/wiki/FrontPage"
9
+ gem.description = "Svengali offers means to manage and operate distributed machines easier than by other tools like shell script"
10
+ gem.email = "ryo.contact [at] gmail.com"
11
+ gem.homepage = "http://sourceforge.jp/projects/svengali/"
12
+ gem.authors = ["Ryo Kanbayashi"]
13
+ gem.add_development_dependency "rspec", ">= 1.2.9"
14
+ gem.add_dependency "net-ssh", ">= 2.0.17"
15
+ gem.add_dependency "net-sftp", ">= 2.0.4"
16
+ # gem is a Gem::Specification... see http://www.rubygems.org/read/chapter/20 for additional settings
17
+ end
18
+ Jeweler::GemcutterTasks.new
19
+ rescue LoadError
20
+ puts "Jeweler (or a dependency) not available. Install it with: gem install jeweler"
21
+ end
22
+
23
+ require 'spec/rake/spectask'
24
+ Spec::Rake::SpecTask.new(:spec) do |spec|
25
+ spec.libs << 'lib' << 'spec'
26
+ spec.spec_files = FileList['spec/**/*_spec.rb']
27
+ end
28
+
29
+ Spec::Rake::SpecTask.new(:rcov) do |spec|
30
+ spec.libs << 'lib' << 'spec'
31
+ spec.pattern = 'spec/**/*_spec.rb'
32
+ spec.rcov = true
33
+ end
34
+
35
+ task :spec => :check_dependencies
36
+
37
+ task :default => :spec
38
+
39
+ require 'rake/rdoctask'
40
+ Rake::RDocTask.new do |rdoc|
41
+ version = File.exist?('VERSION') ? File.read('VERSION') : ""
42
+
43
+ rdoc.rdoc_dir = 'rdoc'
44
+ rdoc.title = "svengali #{version}"
45
+ rdoc.rdoc_files.include('README*')
46
+ rdoc.rdoc_files.include('lib/**/*.rb')
47
+ end
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.2.7.2
Binary file
Binary file
Binary file
Binary file
@@ -0,0 +1,2 @@
1
+ require "svengali/svengali"
2
+
@@ -0,0 +1,78 @@
1
+ #for StringIO
2
+ require "stringio"
3
+
4
+ module Config
5
+
6
+ # if there isn't a file which has specified file name, New file is created.
7
+ def get_config_file(remote_filepath_str)
8
+ # passed @sftp_session is not one of ConfigFile
9
+ return ConfigFile.new(remote_filepath_str,@sftp_session)
10
+ end
11
+
12
+ class ConfigFile
13
+ include FileIO
14
+
15
+ @remote_filepath_str
16
+ @sftp_session
17
+ #Net::SFTP::Request
18
+ @config_file_contents
19
+
20
+ #ssh_session => Net::SFTP::Session
21
+ #ConfigFile class doesn't manage passed sftp_session value
22
+ def initialize(remote_path_str,sftp_session)
23
+ @sftp_session = sftp_session
24
+
25
+ @remote_filepath_str = remote_path_str
26
+ if is_exist(remote_path_str)
27
+ # config_file = @sftp_session.open!(remote_path_str)
28
+ @config_file_contents = get_contents_remote(@remote_filepath_str)
29
+ else
30
+ @config_file_contents = ""
31
+ end
32
+
33
+ end
34
+
35
+ #replace columns which has specified content
36
+ def replace_col(original_col_str,replaced_col_str)
37
+ orig_contents_io = StringIO.new(@config_file_contents)
38
+ replaced_contents_io = StringIO.new()
39
+ orig_contents_io.each_line { |line|
40
+ replaced_contents_io.puts(line.gsub(original_col_str,replaced_col_str))
41
+ }
42
+ orig_contents_io.close()
43
+ replaced_contents_io.close()
44
+
45
+ @config_file_contents = replaced_contents_io.string
46
+ end
47
+
48
+ def append_str(str)
49
+ @config_file_contents += str
50
+ end
51
+
52
+ #remove all columns which contains passed string
53
+ def remove_col_by_str(str)
54
+ orig_contents_io = StringIO.new(@config_file_contents)
55
+ removed_contents_io = StringIO.new()
56
+ orig_contents_io.each_line { |line|
57
+ unless line.index(str)
58
+ removed_contents_io.puts(line)
59
+ end
60
+ }
61
+ orig_contents_io.close()
62
+ removed_contents_io.close()
63
+
64
+ @config_file_contents = removed_contents_io.string
65
+ end
66
+
67
+ #remove columns which matched passed regular expression
68
+ def remove_col_by_regexp(regexp)
69
+ not_inp()
70
+ end
71
+
72
+ #save modified content
73
+ def save
74
+ write_contents_remote(@remote_filepath_str,@config_file_contents)
75
+ end
76
+
77
+ end
78
+ end
@@ -0,0 +1,55 @@
1
+ require "yaml"
2
+
3
+ # manages externarized strings on YAML files
4
+ class ExtStr
5
+ @@command_accessor = nil
6
+ @@path_accessor = nil
7
+
8
+ def self.path()
9
+ unless @@command_accessor && @@path_accessor
10
+ self.init()
11
+ end
12
+
13
+ return @@path_accessor
14
+ end
15
+
16
+ def self.cmd()
17
+ unless @@command_accessor && @@path_accessor
18
+ self.init()
19
+ end
20
+
21
+ return @@command_accessor
22
+ end
23
+
24
+ def self.init()
25
+ @@command_accessor = ExtStrAccessor.new(File::dirname(__FILE__) + "/ext_string/command.yml",$platform_name)
26
+ @@path_accessor = ExtStrAccessor.new( File::dirname(__FILE__) + "/ext_string/path.yml",$platform_name)
27
+ end
28
+ # private_class_method :init
29
+
30
+ end
31
+
32
+ class ExtStrAccessor
33
+ @contents_hash
34
+ @first_level
35
+
36
+ def initialize(file_name_str,first_level_name)
37
+ @contents_hash = YAML.load_file( file_name_str )
38
+ @first_level = first_level_name
39
+ end
40
+
41
+ def [](key)
42
+ val = @contents_hash[@first_level][key]
43
+ if val
44
+ return val
45
+ else
46
+ default_val = @contents_hash["default"][val]
47
+ if default_val
48
+ return default_val
49
+ else
50
+ debug_p "key( #{key.to_s} ) is not found on even default hash!"
51
+ end
52
+ end
53
+ end
54
+
55
+ end
@@ -0,0 +1,6 @@
1
+ default:
2
+ package_install: yum install -y
3
+ debian:
4
+ package_install: apt-get install
5
+
6
+
@@ -0,0 +1,6 @@
1
+ default:
2
+ sshd_config: /etc/ssh/sshd_config
3
+ network_configs: /etc/sysconfig/network-scripts/
4
+ resolver_config: /etc/sysconfig/network-scripts/ifcfg-eth0
5
+ debian:
6
+ network_configs: /etc/network/
@@ -0,0 +1,106 @@
1
+ #in this file methods for file trasfer is defined
2
+ require 'rubygems'
3
+ gem 'net-sftp'
4
+ require 'net/sftp'
5
+
6
+ module FileIO
7
+ BUFFER_SIZE = 1024
8
+
9
+ def push_a_file(local_path,remote_path)
10
+ debug_p("push_a_file from #{local_path} to #{remote_path}")
11
+ @sftp_session.upload!(local_path,remote_path)
12
+ end
13
+
14
+ def pull_a_file(remote_path,local_path)
15
+ debug_p("pull_a_file from #{remote_path} to #{local_path}")
16
+
17
+ begin
18
+ @sftp_session.download!(remote_path,local_path)
19
+ rescue
20
+ debug_p remote_path + " is not found on remote!!"
21
+ return nil
22
+ end
23
+ end
24
+
25
+ # push files on specified dir. only one level.
26
+ # directories are not copied.
27
+ def push_files(local_path,remote_path)
28
+ debug_p("push_files from #{local_path} to #{remote_path}")
29
+ local_dir = Dir.new(local_path)
30
+ local_dir.each{ |path|
31
+ unless File::ftype(local_path + "/" + path) == "directory"
32
+ @sftp_session.upload!(local_path + "/" + path,remote_path + "/" + path)
33
+ end
34
+ }
35
+ end
36
+
37
+ #pull files on specified dir. only one level.
38
+ def pull_files(remote_path,local_path)
39
+ debug_p("pull_files from #{remote_path} to #{local_path}")
40
+ @sftp_session.dir.foreach(remote_path){ |path|
41
+ #unless path.name == "." || path.name == ".."
42
+ #not directory
43
+ unless /^d/ =~ path.longname
44
+ @sftp_session.download!(remote_path + "/" + path.name,local_path + "/" + path.name)
45
+ end
46
+ #end
47
+ }
48
+ end
49
+
50
+ # Note: if there is a directory which has same name with *local_path*, remote_directory is removed before coping directory
51
+ def push_dir(local_path,remote_path)
52
+ debug_p("push_dir from #{local_path} to #{remote_path}")
53
+ begin
54
+ @sftp_session.upload!(local_path,remote_path)
55
+ rescue
56
+ @ssh.exec!("rm -rf #{remote_path}")
57
+ retry
58
+ end
59
+ end
60
+
61
+ def pull_dir(remote_path,local_path)
62
+ debug_p("pull_dir from #{remote_path} to #{local_path}")
63
+ begin
64
+ @sftp_session.download!(remote_path,local_path,:recursive => true)
65
+ rescue
66
+ debug_p remote_path + " is not found on remote!!"
67
+ return nil
68
+ end
69
+ end
70
+
71
+ # return -> boolean :
72
+ def is_exist(remote_path)
73
+ begin
74
+ @sftp_session.stat!(remote_path) { |response|
75
+ #returns whether exists or not
76
+ next response.ok?
77
+ }
78
+ rescue => e
79
+ return false
80
+ end
81
+ end
82
+
83
+
84
+ def get_contents_remote(remote_filepath_str)
85
+ debug_p("get_contents_remote from #{remote_filepath_str}")
86
+ handle = @sftp_session.open!(remote_filepath_str)
87
+ contents = String.new()
88
+ offset = 0
89
+ while (data = @sftp_session.read!(handle, offset, BUFFER_SIZE)) != nil
90
+ contents += data
91
+ offset += BUFFER_SIZE
92
+ end
93
+ @sftp_session.close!(handle)
94
+
95
+ return contents
96
+ end
97
+
98
+ # over writes contens from the start
99
+ def write_contents_remote(remote_filepath_str,contents_str)
100
+ debug_p("write_contents_remote to #{remote_filepath_str}")
101
+ handle = @sftp_session.open!(remote_filepath_str,"w")
102
+ @sftp_session.write!(handle, 0, contents_str)
103
+ @sftp_session.close!(handle)
104
+ end
105
+
106
+ end
@@ -0,0 +1,123 @@
1
+ require "thread"
2
+ require "#{LIBNAME}/ssh"
3
+ require "#{LIBNAME}/config"
4
+ require "#{LIBNAME}/util"
5
+ require "#{LIBNAME}/ext_string"
6
+
7
+ #module Machine
8
+ class MachineMaster
9
+ @@group = ThreadGroup.new
10
+ end
11
+
12
+ class Machine < MachineMaster
13
+ include Config
14
+ include FileIO
15
+
16
+ #fields
17
+ @user_name
18
+ @host
19
+ @ssh
20
+ @sftp_session
21
+ @password
22
+ @passphrase
23
+ @private_key_path
24
+
25
+ attr_reader :ssh
26
+
27
+ def initialize(host=nil)
28
+ if host == nil #substitute of constructor which has no argument
29
+ else
30
+ @host = host.to_s()
31
+ initialize()
32
+ end
33
+ end
34
+
35
+ def cleanup
36
+ debug_p "start cleanup instance for " + @host
37
+ @sftp_session.close_channel()
38
+ @ssh.close()
39
+ debug_p "finished cleanup instance for " + @host
40
+ # @@group.list.each {|th| th.join }
41
+ end
42
+
43
+ # def set_auth_info(user_name)
44
+ # @user_name = user_name
45
+ # end
46
+
47
+ def set_auth_info(user_name,password = nil)
48
+ @user_name = user_name
49
+ @password = password
50
+ end
51
+
52
+ def set_auth_info_pki(user_name,passphrase,private_key_path)
53
+ @user_name = user_name
54
+ @passphrase = passphrase
55
+ @private_key_path = private_key_path
56
+ end
57
+
58
+ def establish_session()
59
+ debug_p "start establish_session to " + @host
60
+ # Spawn worker threads
61
+
62
+ th = Thread.new do
63
+ debug_p "Initialization of Machine ##{@host} is started."
64
+ if @private_key_path
65
+ if @user_name && @passphrase
66
+ @ssh = SSH.new(@host,@user_name,@passphrase)
67
+ else
68
+ debug_p "please set user name and password when you want to use public key authentication"
69
+ exit()
70
+ end
71
+ elsif @user_name && @password
72
+ @ssh = SSH.new(@host,@user_name,@password)
73
+ elsif @user_name
74
+ @ssh = SSH.new(@userneme)
75
+ else
76
+ debug_p "please set user name at leaset"
77
+ exit()
78
+ end
79
+ debug_p "Initialization of Machine ##{@host} is finished."
80
+
81
+ @sftp_session = @ssh.sftp_session
82
+ @@group.add(th)
83
+ end
84
+
85
+ #wait until finishing initialize of @ssh object
86
+ while @ssh == nil
87
+ sleep(1)
88
+ end
89
+
90
+ debug_p "finished establish_session to " + @host
91
+ end
92
+
93
+ def exec(command_str)
94
+ return @ssh.exec(command_str)
95
+ end
96
+
97
+ def exec!(command_str,timeout = nil)
98
+ return @ssh.exec!(command_str,timeout)
99
+ end
100
+
101
+ # call exec!( command ) on specified path
102
+ # TODO: change function name to exec_on!
103
+ def exec_on!(command_str,current_path_str)
104
+ exec!("cd #{current_path_str};" + command_str)
105
+ end
106
+
107
+ # execute local script on remote
108
+ # current_path_str -> string: if change of directory is not needed, please pass "."
109
+ # use remote /tmp directory to store script file
110
+ # TODO: change function name to exec_script_on!
111
+ def exec_script_on(script_path_str,arguments_str,current_path_str)
112
+ fname_str = File.basename(script_path_str)
113
+ rempte_path_str = "/tmp/" + fname_str
114
+ push_a_file(script_path_str,rempte_path_str)
115
+ exec_on!("sh #{rempte_path_str} " + arguments_str,current_path_str)
116
+ end
117
+
118
+ def sftp()
119
+ return @ssh.sftp_session
120
+ end
121
+
122
+ end
123
+ #end