forj 1.0.7 → 1.0.8

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
  SHA1:
3
- metadata.gz: 70f1b264464790bfae435e9dcfb4fda06d646bc7
4
- data.tar.gz: 1e54b8faf466d33cb3147b38a26473a2fd368319
3
+ metadata.gz: 8ae496ebb4a7235af6bb457cb453a6756d2a0642
4
+ data.tar.gz: f2b320eb7ea1a74f9333c1225c9fa6ded4ea4c11
5
5
  SHA512:
6
- metadata.gz: b539bf62bd365a93000a0b5abf5883f4328d624fa5577f621add143fbaadfa309bc881b86f2984a91a6062aaef048ef8190d7895dd16f677e3ec391a3d9e1c2e
7
- data.tar.gz: a42889ff7406624e986c36c59c13b9bb683509e129cfbc8ef8be42407bd6f267f75d3a6475390a38dfa5542bd556b0a5e2083841ae01169c0940be8bdaa32d7e
6
+ metadata.gz: 104dfb17330577fd62ad5495f4fa919fdf552f0ceac21891192e34b8ca7c059d2b65dbfc274aac89ae604e6a80ab8af73c07662e0ff2b4103c40e5da6a43ae5c
7
+ data.tar.gz: 95c65f260efee949a181a5549c5883309eaec1158b76939d85db356e74e4ce6ece8d3ec7a144db66710b6168e8d5a08ccb395785de5408089e66d360a89e90aa
data/bin/forj CHANGED
@@ -387,6 +387,7 @@ Several data will be requested like:
387
387
  o_cloud = Forj::CloudConnection.connect(account)
388
388
  o_cloud.setup(:forge, sAccountName)
389
389
  o_cloud.config.ac_save
390
+ PrcLib.high_level_msg("\nAccount %s '%s' saved.\n", sProvider, sAccountName)
390
391
  end
391
392
  end
392
393
 
data/forj/defaults.yaml CHANGED
@@ -128,15 +128,21 @@
128
128
  :account: true
129
129
  :ask_step: 2
130
130
  :after: :keypair_name
131
+ :pre_step_function: :forj_cloud_keypair_coherent?
131
132
  :post_step_function: :forj_setup_keypairs_files
132
133
  :keypair_path:
133
- :desc: "Forj internal copy of private and public key pair files "
134
+ :desc: "Contains the full path to the :keypair_base."
135
+ :default_value: "<%= Forj.keypairs_path %>"
136
+ :keypair_base:
137
+ :desc: "Contains the key file base name without .pem/.pub."
134
138
  :keypair_name:
135
139
  :desc: "keypair name defined in your cloud to access your server. By default we named it 'forj'. If it doesn't exist, it will be created."
136
140
  :required: true
137
141
  :default_value: "forj"
138
142
  :account: true
139
143
  :ask_step: 2
144
+ :pre_step_function: :update_keypair_config
145
+ :post_step_function: :forj_check_cloud_keypair
140
146
  :auth_uri:
141
147
  :desc: "Generic service auth url"
142
148
  :account_exclusive: true
data/forj.gemspec CHANGED
@@ -19,8 +19,8 @@ Gem::Specification.new do |s|
19
19
  s.name = 'forj'
20
20
  s.homepage = 'https://www.forj.io'
21
21
 
22
- s.version = '1.0.7'
23
- s.date = '2015-03-23'
22
+ s.version = '1.0.8'
23
+ s.date = '2015-03-27'
24
24
  s.summary = 'forj command line'
25
25
  s.description = 'forj cli - See https://www.forj.io for documentation/information'
26
26
 
@@ -52,7 +52,7 @@ Gem::Specification.new do |s|
52
52
  s.add_runtime_dependency 'json', '1.7.5'
53
53
  s.add_runtime_dependency 'bundler'
54
54
  s.add_runtime_dependency 'nokogiri','1.5.11'
55
- s.add_runtime_dependency 'lorj', '~> 1.0.7'
55
+ s.add_runtime_dependency 'lorj', '~> 1.0.8'
56
56
 
57
57
  s.add_development_dependency "rake", "~> 10.0"
58
58
  s.add_development_dependency "rspec", "~> 3.1.0"
data/lib/destroy.rb CHANGED
@@ -36,62 +36,77 @@ module Forj
36
36
  o_forge = o_cloud.get(:forge, name)
37
37
 
38
38
  if o_forge[:servers].count > 0
39
- destroy_server(o_cloud, o_forge, options, account)
39
+ destroy_server(o_cloud, o_forge, options)
40
40
  else
41
41
  PrcLib.high_level_msg("No server(s) found on forge instance '%s'.\n",
42
42
  name)
43
43
  end
44
44
  end
45
45
 
46
- def self.destroy_server(o_cloud, o_forge, options, account)
46
+ def self.destroy_server(o_cloud, o_forge, options)
47
47
  if options[:force]
48
48
  # Destroy all servers found
49
49
  o_cloud.delete(:forge)
50
50
  else
51
- server_list = get_server_list(o_forge)
51
+ server_list, servers_id = get_server_list(o_forge)
52
52
 
53
- o_server_number = get_server_index(server_list)
53
+ server_name = choose_server(server_list)
54
54
 
55
- if o_server_number >= 0 && o_server_number < o_forge[:servers].count
56
- # Destroy selected server
57
- account.set(:forge_server, o_forge[:servers][o_server_number][:id])
55
+ case server_name
56
+ when 'abort'
57
+ PrcLib.high_level_msg("No server destroyed on your demand.\n", name)
58
+ return
59
+ when 'all'
60
+ # Destroy all servers found
58
61
  o_cloud.delete(:forge)
62
+ return
63
+ else
64
+ # Destroy selected server
65
+ found = server_name.match(/ - (.*)$/)
66
+ if found
67
+ o_cloud.delete(:forge, :forge_server => found[1])
68
+ else
69
+ o_cloud.delete(:forge, :forge_server => servers_id[server_name][0])
70
+ end
59
71
  end
60
-
61
- # Destroy all servers found
62
- o_cloud.delete(:forge) if o_server_number == server_list.index('all')
63
- # esc
64
- PrcLib.high_level_msg("No server destroyed on your demand.\n",
65
- name
66
- ) if o_server_number == server_list.index('esc')
67
72
  end
68
73
  end
69
74
 
70
- def self.get_server_list(o_forge)
75
+ def self.get_server_list(forge)
71
76
  # Ask the user to get server(s) to destroy
72
77
  server_list = []
73
- index = 0
78
+ servers_id = {}
79
+
80
+ forge[:servers].each do |_type, server|
81
+ server_name = server[:name]
82
+ if servers_id.key?(server_name)
83
+ servers_id[server_name] << server[:id]
84
+ else
85
+ servers_id[server_name] = [server[:id]]
86
+ end
87
+ end
74
88
 
75
- o_forge[:servers].each do |server|
76
- server_list[index] = server[:name]
77
- index += 1
89
+ servers_id.each do |name, servers|
90
+ if servers.length > 1
91
+ servers.each { |id| server_list << name + ' - ' + id }
92
+ else
93
+ server_list << name
94
+ end
78
95
  end
79
96
 
80
97
  server_list << 'all'
81
- server_list << 'esc'
98
+ server_list << 'abort'
82
99
 
83
- server_list
100
+ [server_list, servers_id]
84
101
  end
85
102
 
86
- def self.get_server_index(server_list)
87
- say('Select the index of the server you want to destroy')
103
+ def self.choose_server(server_list)
104
+ say('Please, choose what you want to destroy')
88
105
  value = choose do |q|
89
106
  q.choices(*server_list)
90
107
  end
91
108
 
92
- o_server_number = server_list.index(value)
93
-
94
- o_server_number
109
+ value
95
110
  end
96
111
  end
97
112
  end
data/lib/forj/ForjCore.rb CHANGED
@@ -66,6 +66,7 @@ class Lorj::BaseDefinition
66
66
  obj_needs :data, :os_enckey
67
67
  obj_needs :data, :account_id
68
68
  obj_needs :data, :account_key
69
+ obj_needs :data, :auth_uri
69
70
  obj_needs_optional
70
71
 
71
72
  # If requested by user, ask Maestro to manage the DNS.
@@ -107,4 +108,5 @@ class Lorj::BaseDefinition
107
108
  obj_needs :CloudObject, :public_ip, :for => [:create_e]
108
109
  obj_needs :CloudObject, :keypairs, :for => [:create_e]
109
110
  obj_needs :data, :blueprint
111
+ obj_needs :data, :forge_server, :for => [:delete_e]
110
112
  end
@@ -31,17 +31,22 @@ INFRA_VERSION = '0.0.37'
31
31
  # Functions for boot - build_forge
32
32
  class ForjCoreProcess
33
33
  def build_forge(sObjectType, hParams)
34
- forge_exist?(sObjectType)
34
+ # TODO: To be replaced by a migration task at install phase.
35
+ update_keypair_config
35
36
 
36
- o_server = hParams.refresh[:server, :ObjectData]
37
+ o_forge = forge_get_or_create(sObjectType, hParams)
37
38
 
38
- boot_options = boot_keypairs(hParams)
39
+ # Refresh full data on the server found or created.
40
+ server = controller_get(:server, o_forge[:servers, 'maestro'][:id])
41
+ o_forge[:servers, 'maestro'] = server
42
+
43
+ boot_options = boot_keypairs(server)
39
44
 
40
45
  # Define the log lines to get and test.
41
46
  config.set(:log_lines, 5)
42
47
 
43
48
  PrcLib.info("Maestro server '%s' id is '%s'.",
44
- o_server[:name], o_server[:id])
49
+ server[:name], server[:id])
45
50
  # Waiting for server to come online before assigning a public IP.
46
51
 
47
52
  s_status = :checking
@@ -49,11 +54,10 @@ class ForjCoreProcess
49
54
 
50
55
  o_address = hParams.refresh[:public_ip, :ObjectData]
51
56
 
52
- s_status = active_server?(o_server, o_address, boot_options[:keys],
53
- boot_options[:coherent], s_status
54
- )
57
+ s_status = active_server?(server, o_address, boot_options[:keys],
58
+ boot_options[:coherent], s_status)
55
59
 
56
- till_server_active(s_status, o_server, o_address, boot_options)
60
+ till_server_active(s_status, server, o_address, boot_options)
57
61
 
58
62
  o_forge = get_forge(sObjectType, config[:instance_name], hParams)
59
63
 
@@ -61,49 +65,91 @@ class ForjCoreProcess
61
65
  o_forge
62
66
  end
63
67
 
64
- def forge_exist?(sObjectType)
68
+ def forge_get_or_create(sObjectType, hParams)
65
69
  o_forge = process_get(sObjectType, config[:instance_name])
66
70
  if o_forge.empty? || o_forge[:servers].length == 0
67
71
  PrcLib.high_level_msg("\nBuilding your forge...\n")
68
72
  process_create(:internet_server)
73
+ o_forge[:servers, 'maestro'] = hParams.refresh[:server]
69
74
  else
70
- load_existing_forge(o_forge)
75
+ o_forge = load_existing_forge(o_forge, hParams)
71
76
  end
77
+ o_forge
72
78
  end
73
79
 
74
- def load_existing_forge(o_forge)
75
- o_forge[:servers].each do |oServerToFind|
76
- if /^maestro\./ =~ oServerToFind[:name]
77
- process_get(:server, oServerToFind[:id])
78
- end
79
- end
80
+ def load_existing_forge(o_forge, hParams)
80
81
  PrcLib.high_level_msg("\nChecking your forge...\n")
81
82
 
82
- o_server = data_objects(:server, :ObjectData)
83
+ o_server = o_forge[:servers, 'maestro']
83
84
  if o_server
84
- o_ip = process_query(:public_ip, :server_id => o_server[:id])
85
- register o_ip[0] if o_ip.length > 0
86
- process_create(:keypairs)
85
+ query = { :server_id => o_server[:id] }
86
+ register(o_server)
87
+ o_ip = process_query(:public_ip, query)
88
+ register(o_ip[0]) if o_ip.length > 0
87
89
  else
88
90
  PrcLib.high_level_msg("\nYour forge exist, without maestro." \
89
91
  " Building Maestro...\n")
90
92
  process_create(:internet_server)
93
+ o_forge[:servers, 'maestro'] = hParams.refresh[:server]
91
94
 
92
95
  PrcLib.high_level_msg("\nBuilding your forge...\n")
93
96
  end
97
+ o_forge
94
98
  end
99
+ end
95
100
 
96
- def boot_keypairs(params)
97
- o_server = params[:server, :ObjectData]
98
- h_keys = params[:keypairs]
101
+ # Functions for boot - build_forge
102
+ class ForjCoreProcess
103
+ def boot_keypairs(server)
104
+ h_keys = process_create(:keypairs)
105
+ keypair = process_get(:keypairs, server[:key_name])
106
+
107
+ h_keys = choose_best_kp(h_keys, keypair, server[:name])
108
+
109
+ h_keys[:keys] = File.join(h_keys[:keypair_path],
110
+ h_keys[:private_key_name])
111
+
112
+ unless h_keys[:coherent]
113
+ PrcLib.warning("The local keypair '%s' public key and '%s' server's "\
114
+ "public key are different.\n"\
115
+ "You won't be able to access it until "\
116
+ 'you get a copy of the key used to create the server.'\
117
+ "\nPublic key found in the cloud:\n%s",
118
+ h_keys[:name], server[:name], keypair[:public_key])
119
+ return h_keys
120
+ end
99
121
 
100
- if h_keys.nil? || o_server[:key_name] != h_keys[:name]
101
- h_keys = process_get(:keypairs, o_server[:key_name])
122
+ unless h_keys[:private_key_exist?]
123
+ PrcLib.warning("The local keypair '%s' private key '%s' is not found. "\
124
+ "You won't be able to access '%s' until you get a copy"\
125
+ 'of the private key use to create the server.'\
126
+ "\nPublic key found in the cloud:\n%s",
127
+ h_keys[:keys], server[:name], keypair[:public_key])
102
128
  end
103
- private_key_file = File.join(h_keys[:keypair_path],
104
- h_keys[:private_key_name])
105
129
 
106
- { :keys => private_key_file, :coherent => h_keys[:coherent] }
130
+ h_keys
131
+ end
132
+
133
+ def choose_best_kp(predef_keypair, server_keypair, server_name)
134
+ if server_keypair[:name] != predef_keypair[:name]
135
+ if coherent_keypair?(predef_keypair, server_keypair)
136
+ PrcLib.warning("Server '%s' is using keypair name '%s' instead of the"\
137
+ " your account keypair name '%s'.\n"\
138
+ 'Your predefined keypair name is compatible with '\
139
+ 'that server. (public key identical), so Forj will use'\
140
+ " '%s' by default",
141
+ server_name, server_keypair[:name],
142
+ server_keypair[:name], server_keypair[:name])
143
+ return predef_keypair
144
+ end
145
+ PrcLib.warning("Server '%s' is using keypair name '%s' instead of the "\
146
+ "your account keypair name '%s'.\n"\
147
+ "Forj will try to find and use a local keypair name '%s'"\
148
+ ' instead.', server_name, server_keypair[:name],
149
+ predef_keypair[:name], server_keypair[:name])
150
+ return server_keypair
151
+ end
152
+ predef_keypair
107
153
  end
108
154
 
109
155
  def active_server?(o_server, o_address, private_key_file,
@@ -112,22 +158,20 @@ class ForjCoreProcess
112
158
  if o_server[:attrs][:status] == :active
113
159
  image = server_get_image o_server
114
160
 
115
- s_msg = <<-END
116
- Your forj Maestro server is up and running and is publically accessible
117
- through IP '%s'.
118
-
119
- You can connect to '%s' with:
120
- ssh %s@%s -o StrictHostKeyChecking=no -i %s
121
- END
122
- s_msg = format(s_msg, o_address[:public_ip], o_server[:name],
123
- image[:ssh_user], o_address[:public_ip], private_key_file
124
- )
161
+ s_msg = format('Your forj Maestro server is up and running and is '\
162
+ "publically accessible through IP '%s'.\n\n"\
163
+ "You can connect to '%s' with:\n"\
164
+ 'ssh %s@%s -o StrictHostKeyChecking=no -i ',
165
+ o_address[:public_ip], o_server[:name],
166
+ image[:ssh_user], o_address[:public_ip])
125
167
 
126
- unless keypair_coherent
127
- s_msg += "\n" + ANSI.bold(
128
- 'Unfortunatelly'
129
- ) + ' your current keypair is not usable to connect to your server.' \
130
- "\n" + 'You need to fix this issue to gain access to your server.'
168
+ if keypair_coherent
169
+ s_msg += private_key_file
170
+ else
171
+ s_msg += ANSI.red(ANSI.bold('<no valid private key found>')) + "\n\n" +
172
+ ANSI.bold('Unfortunatelly') + ', Forj was not able to find a '\
173
+ 'valid keypair to connect to your server.' \
174
+ "\nYou need to fix this issue to gain access to your server."
131
175
  end
132
176
  PrcLib.info(s_msg)
133
177
 
@@ -223,8 +267,8 @@ class ForjCoreProcess
223
267
  "%s\n"\
224
268
  "#{highlight}\n"\
225
269
  "The server '%s' is not providing any output log for"\
226
- " more than 5 minutes.\nPlease review the current"\
227
- 'output show below to determine if this a normal '\
270
+ " more than 5 minutes.\nPlease review the current "\
271
+ 'output shown below to determine if this is a normal '\
228
272
  "situation.\nYou can connect to the server if you "\
229
273
  "want to.\nTo connect, use:\n"\
230
274
  'ssh %s@%s -o StrictHostKeyChecking=no -i %s',
@@ -425,7 +469,7 @@ class ForjCoreProcess
425
469
 
426
470
  def display_servers_with_ip(o_forge, s_msg)
427
471
  i_count = 0
428
- o_forge[:servers].each do |server|
472
+ o_forge[:servers].each do |_type, server|
429
473
  next if /^maestro\./ =~ server[:name]
430
474
  register(server)
431
475
  o_ip = process_query(:public_ip, :server_id => server[:id])
@@ -510,14 +554,15 @@ class ForjCoreProcess
510
554
  'PUPPET_DEBUG' => 'True',
511
555
  'image_name' => hParams[:image_name],
512
556
  'key_name' => hParams[:keypair_name],
513
- 'hpcloud_priv' => Base64.strict_encode64(
514
- hpcloud_priv
515
- ).gsub('=', '') # Remove pad
557
+ # Remove pad
558
+ 'hpcloud_priv' => Base64.strict_encode64(hpcloud_priv).gsub('=', ''),
559
+ 'compute_os_auth_url' => hParams[:auth_uri]
516
560
  }
517
561
 
518
562
  if hParams[:dns_service]
519
563
  h_meta['dns_zone'] = hParams[:dns_service]
520
564
  h_meta['dns_tenantid'] = hParams[:dns_tenant_id]
565
+ h_meta['dns_auth_url'] = hParams[:auth_uri]
521
566
  end
522
567
  # If requested by user, ask Maestro to instantiate a blueprint.
523
568
  h_meta['blueprint'] = hParams[:blueprint] if hParams[:blueprint]
@@ -878,14 +923,21 @@ class ForjCoreProcess
878
923
  cmd = format(
879
924
  "%s '%s' '%s' '%s' '%s' '%s' '%s' '%s'",
880
925
  bootstrap, # script
881
- PrcLib.data_path, # $1 = Forj data base dir
926
+ # $1 = Forj data base dir
927
+ PrcLib.data_path,
882
928
  # $2 = Maestro repository dir
883
929
  hParams[:maestro_repository, :maestro_repo],
884
- config[:bootstrap_dirs], # $3 = Bootstrap directories
885
- config[:bootstrap_extra_dir], # $4 = Bootstrap extra directory
886
- meta_data, # $5 = meta_data (string)
887
- mime_cmd, # $6: mime script file to execute.
888
- mime # $7: mime file generated.
930
+ # $3 = Bootstrap directories
931
+ hParams[:infra_repository, :infra_repo] + ' ' +
932
+ config.get(:bootstrap_dirs, ''),
933
+ # $4 = Bootstrap extra directory
934
+ config[:bootstrap_extra_dir],
935
+ # $5 = meta_data (string)
936
+ meta_data,
937
+ # $6: mime script file to execute.
938
+ mime_cmd,
939
+ # $7: mime file generated.
940
+ mime
889
941
  )
890
942
 
891
943
  run_userdata_cmd(cmd, bootstrap, mime)
@@ -927,11 +979,15 @@ class ForjCoreProcess
927
979
  end
928
980
  # end
929
981
  end
982
+
930
983
  # Check files existence
931
- def forj_check_keypairs_files(keypath)
984
+ def forj_check_keypairs_files(input_pathbase)
932
985
  key_name = config.get(:keypair_name)
933
986
 
934
- keys_entered = keypair_detect(key_name, keypath)
987
+ keypair_path = File.expand_path(File.dirname(input_pathbase))
988
+ keypair_base = File.expand_path(File.basename(input_pathbase))
989
+ keys_entered = keypair_detect(key_name, keypair_path, keypair_base)
990
+
935
991
  if !keys_entered[:private_key_exist?] && !keys_entered[:public_key_exist?]
936
992
  if agree('The key you entered was not found. Do you want to create' \
937
993
  ' this one?')
@@ -944,30 +1000,69 @@ class ForjCoreProcess
944
1000
  true
945
1001
  end
946
1002
 
947
- def duplicate_keyname?(keys_imported, keys, key_name)
948
- if keys_imported && keys_imported[:key_basename] != keys[:key_basename] &&
949
- Forj.keypairs_path != keys[:keypair_path]
950
- PrcLib.warning("The private key '%s' was assigned to a different private"\
951
- " key file '%s'.\nTo not overwrite it, we recommend you"\
952
- ' to choose a different keypair name.',
953
- keys, keys_imported[:key_basename])
954
- new_key_name = key_name
955
- s_msg = 'Please, provide a different keypair name:'
956
- while key_name == new_key_name
957
- new_key_name = ask(s_msg) do |q|
958
- q.validate = /.+/
959
- end
960
- new_key_name = new_key_name.to_s
961
- s_msg = 'Incorrect. You have to choose a keypair name different' \
962
- " than '#{key_name}'. If you want to interrupt, press Ctrl-C and" \
963
- ' retry later.\nSo, please, provide a different keypair' \
964
- ' name:' if key_name == new_key_name
1003
+ # Function to identify if the keypair name has already been imported.
1004
+ # If so, we can't change the original files used to import it.
1005
+ # The script will ask for another keypair_name.
1006
+ #
1007
+ # It will loop until keyname is new or until files originally used
1008
+ # is identical.
1009
+ def check_about_imported_key(setup_keys, key_name)
1010
+ loop do
1011
+ keys_imported = nil
1012
+ if config.local_exist?(key_name.to_sym, :imported_keys)
1013
+ keys_imported = keypair_detect(key_name,
1014
+ config.local_get(key_name.to_sym,
1015
+ :imported_keys))
1016
+ end
1017
+
1018
+ return setup_keys if keys_imported.nil?
1019
+
1020
+ unless keys_imported[:private_key_exist?] ||
1021
+ keys_imported[:public_key_exist?]
1022
+ PrcLib.warning("The local keypair '%s' imported files do not exist "\
1023
+ 'anymore. Removed from imported_keys.', key_name)
1024
+ local_del(key_name.to_sym, :imported_keys)
1025
+ break
965
1026
  end
966
- key_name = new_key_name
1027
+
1028
+ setup_keybase = File.join(setup_keys[:keypair_path],
1029
+ setup_keys[:key_basename])
1030
+ imported_keybase = File.join(keys_imported[:keypair_path],
1031
+ keys_imported[:key_basename])
1032
+
1033
+ break if setup_keybase == imported_keybase
1034
+
1035
+ PrcLib.warning("You entered a keypair base file '%s' for keypair name "\
1036
+ "'%s'. Originally, this keypair name was created from "\
1037
+ "'%s' instead.\n"\
1038
+ 'To not overwrite it, we recommend you'\
1039
+ ' to choose a different keypair name.',
1040
+ setup_keybase, key_name, imported_keybase)
1041
+ key_name = _keypair_files_ask(key_name)
967
1042
  config.set(:key_name, key_name)
968
- keys = keypair_detect(key_name, key_path)
1043
+
1044
+ setup_keys = keypair_detect(key_name,
1045
+ setup_keys[:keypair_path],
1046
+ setup_keys[:key_basename])
1047
+ end
1048
+ setup_keys
1049
+ end
1050
+
1051
+ # Function to change the keypair name, as already used.
1052
+ def _keypair_files_ask(key_name)
1053
+ new_key_name = key_name
1054
+ s_msg = 'Please, provide a different keypair base file:'
1055
+ while key_name == new_key_name
1056
+ new_key_name = ask(s_msg) do |q|
1057
+ q.validate = /.+/
1058
+ end
1059
+ new_key_name = new_key_name.to_s
1060
+ s_msg = 'Incorrect. You have to choose a keypair base file different'\
1061
+ " than '#{key_name}'. If you want to interrupt, press Ctrl-C."\
1062
+ "\nSo, please, provide a different keypair"\
1063
+ ' name:' if key_name == new_key_name
969
1064
  end
970
- keys
1065
+ new_key_name
971
1066
  end
972
1067
 
973
1068
  def create_keys_automatically(keys, private_key_file)
@@ -990,18 +1085,26 @@ end
990
1085
 
991
1086
  # Functions for setup
992
1087
  class ForjCoreProcess
1088
+ # Import the keypair base files setup by user in forj keypair files.
1089
+ #
1090
+ # This function is can be executed only if we copy files to internal
1091
+ # forj keypair storage. Otherwise this update is ignored.
993
1092
  def save_sequences(private_key_file, forj_private_key_file,
994
1093
  public_key_file, forj_public_key_file, key_name
995
1094
  )
996
1095
  PrcLib.info('Importing key pair to FORJ keypairs list.')
1096
+
997
1097
  FileUtils.copy(private_key_file, forj_private_key_file)
998
1098
  FileUtils.copy(public_key_file, forj_public_key_file)
999
1099
  # Attaching this keypair to the account
1000
1100
  config.set(:keypair_name, key_name, :name => 'account')
1001
- config.set(:keypair_path, forj_private_key_file, :name => 'account')
1002
- config.local_set(key_name.to_s, private_key_file, :imported_keys)
1101
+ config.local_set(key_name.to_sym, private_key_file, :imported_keys)
1003
1102
  end
1004
1103
 
1104
+ # Update the forj keypair base files copy from the original base files.
1105
+ #
1106
+ # This function is can be executed only if we copy files to internal
1107
+ # forj keypair storage. Otherwise this update is ignored.
1005
1108
  def save_md5(private_key_file, forj_private_key_file,
1006
1109
  public_key_file, forj_public_key_file
1007
1110
  )
@@ -1029,9 +1132,9 @@ end
1029
1132
 
1030
1133
  # Functions for setup
1031
1134
  class ForjCoreProcess
1032
- def save_internal_key(forj_private_key_file, keys)
1135
+ def save_internal_key(keys)
1033
1136
  # Saving internal copy of private key file for forj use.
1034
- config.set(:keypair_path, forj_private_key_file, :name => 'account')
1137
+ config.set(:keypair_base, keys[:keypair_name], :name => 'account')
1035
1138
  PrcLib.info("Configured forj keypair '%s' with '%s'",
1036
1139
  keys[:keypair_name],
1037
1140
  File.join(keys[:keypair_path], keys[:key_basename])
@@ -1039,19 +1142,17 @@ class ForjCoreProcess
1039
1142
  end
1040
1143
 
1041
1144
  # keypair_files post setup
1145
+ #
1146
+ # This function will get the keypair_files setup by user and it will:
1147
+ #
1148
+ # * In case keypair already exist, check if imported files is identical.
1149
+ # * Create SSH keys if missing (ssh-keygen - create_keys_automatically)
1150
+ # * exit if :keypair_change is not set to the internal forj dir.
1151
+ # * For new keys, copy new files and keep the original files import place.
1152
+ # * For existing keys, update them from their original places (imported from)
1153
+ # * done
1042
1154
  def forj_setup_keypairs_files
1043
- # Getting Account keypair information
1044
- key_name = config[:keypair_name]
1045
- key_path = File.expand_path(config[:keypair_files])
1046
-
1047
- keys_imported = nil
1048
- keys_imported = keypair_detect(
1049
- key_name,
1050
- config.local_get(key_name, :imported_keys)
1051
- ) if config.local_exist?(key_name, :imported_keys)
1052
- keys = keypair_detect(key_name, key_path)
1053
-
1054
- keys = duplicate_keyname?(keys_imported, keys, key_name)
1155
+ keys = check_setup_keypair
1055
1156
 
1056
1157
  private_key_file = File.join(keys[:keypair_path], keys[:private_key_name])
1057
1158
  public_key_file = File.join(keys[:keypair_path], keys[:public_key_name])
@@ -1059,38 +1160,87 @@ class ForjCoreProcess
1059
1160
  # Creation sequences
1060
1161
  create_keys_automatically(keys, private_key_file)
1061
1162
 
1062
- forj_private_key_file = File.join(Forj.keypairs_path, key_name)
1063
- forj_public_key_file = File.join(Forj.keypairs_path, key_name + '.pub')
1163
+ if Forj.keypairs_path != config[:keypair_path]
1164
+ # Do not save in a config keypair_path not managed by forj.
1165
+ save_internal_key(keys)
1166
+ return true
1167
+ end
1168
+
1169
+ forj_private_key_file = File.join(Forj.keypairs_path, keys[:keypair_name])
1170
+ forj_public_key_file = File.join(Forj.keypairs_path,
1171
+ keys[:keypair_name] + '.pub')
1064
1172
 
1065
1173
  # Saving sequences
1066
- if keys[:keypair_path] != Forj.keypairs_path
1067
- if !File.exist?(forj_private_key_file) ||
1068
- !File.exist?(forj_public_key_file)
1069
- save_sequences(private_key_file, forj_private_key_file,
1070
- public_key_file, forj_public_key_file, key_name
1071
- )
1072
- else
1073
- save_md5(private_key_file, forj_private_key_file,
1074
- public_key_file, forj_public_key_file
1075
- )
1076
- end
1174
+ if !File.exist?(forj_private_key_file) || !File.exist?(forj_public_key_file)
1175
+ save_sequences(private_key_file, forj_private_key_file,
1176
+ public_key_file, forj_public_key_file, keys[:keypair_name])
1177
+ else
1178
+ save_md5(private_key_file, forj_private_key_file,
1179
+ public_key_file, forj_public_key_file)
1077
1180
  end
1078
1181
 
1079
- save_internal_key(forj_private_key_file, keys)
1080
- true # forj_setup_keypairs_files successfull
1182
+ save_internal_key(keys)
1183
+ true # forj_setup_keypairs_files successful
1184
+ end
1185
+
1186
+ def check_setup_keypair
1187
+ key_name = config[:keypair_name]
1188
+ setup_keypair_path = File.expand_path(File.dirname(config[:keypair_files]))
1189
+ setup_keypair_base = File.basename(config[:keypair_files])
1190
+
1191
+ setup_keys = keypair_detect(key_name, setup_keypair_path,
1192
+ setup_keypair_base)
1193
+
1194
+ # Request different keypair_name, if exist and already imported from another
1195
+ # :keypair_files
1196
+ if config[:keypair_path] == Forj.keypairs_path
1197
+ check_about_imported_key(setup_keys, key_name)
1198
+ else
1199
+ setup_keys
1200
+ end
1201
+ end
1202
+
1203
+ # TODO: Change this by a migration function called at install time.
1204
+
1205
+ # Function to convert unclear data structure keypair_path, splitted.
1206
+ # Update config with keypair_base and keypair_path - forj 1.0.8
1207
+ #
1208
+ # * split it in path and base.
1209
+ # * Fix existing config about path&base (update_keypair_config)
1210
+ # * save it in account file respectively as :keypair_path and :keypair_base
1211
+ #
1212
+ # Used in keypair_name pre-step at setup time.
1213
+ # return true to not skip the data.
1214
+ #
1215
+ def update_keypair_config(_ = nil)
1216
+ %w(local account).each do |config_name|
1217
+ next if config.exist?(:keypair_base, :names => [config_name])
1218
+
1219
+ keypair_path = config.get(:keypair_path, nil, :name => config_name)
1220
+
1221
+ options = { :name => config_name }
1222
+ options.merge!(:section => :default) if config_name == 'local'
1223
+ config.set(:keypair_base, File.basename(keypair_path), options)
1224
+ config.set(:keypair_path, File.dirname(keypair_path), options)
1225
+ end
1226
+ true
1081
1227
  end
1082
1228
 
1083
1229
  def forj_dns_settings
1230
+ config[:dns_settings] = false
1231
+
1232
+ return true unless forj_dns_supported?
1233
+
1084
1234
  s_ask = 'Optionally, you can ask Maestro to use/manage a domain name on' \
1085
1235
  " your cloud. It requires your DNS cloud service to be enabled.\nDo" \
1086
1236
  ' you want to configure it?'
1087
- config.set(:dns_settings, agree(s_ask))
1237
+ config[:dns_settings] = agree(s_ask)
1088
1238
  true
1089
1239
  end
1090
1240
 
1091
1241
  def forj_dns_settings?(sKey)
1092
1242
  # Return true to ask the question. false otherwise
1093
- unless config.get(:dns_settings)
1243
+ unless config[:dns_settings]
1094
1244
  section = Lorj.data.first_section(sKey)
1095
1245
  config.del(sKey, :name => 'account', :section => section)
1096
1246
  return false # Do not ask
@@ -1098,6 +1248,19 @@ class ForjCoreProcess
1098
1248
  true
1099
1249
  end
1100
1250
 
1251
+ def forj_dns_supported?
1252
+ unless config[:provider] == 'hpcloud'
1253
+ PrcLib.message("maestro running under '%s' provider currently do "\
1254
+ "support DNS setting.\n", config.get(:provider))
1255
+ config[:dns_settings] = false
1256
+ return false # Do not ask
1257
+ end
1258
+ true
1259
+ end
1260
+ end
1261
+
1262
+ # Functions for setup
1263
+ class ForjCoreProcess
1101
1264
  def setup_tenant_name
1102
1265
  # TODO: To re-introduce with a Controller call instead.
1103
1266
  o_ssl_error = SSLErrorMgt.new # Retry object
@@ -1122,13 +1285,49 @@ class ForjCoreProcess
1122
1285
  end
1123
1286
  @oConfig.set('tenants', tenants)
1124
1287
  end
1288
+
1289
+ # post process after asking keypair name
1290
+ # return true go to next step
1291
+ # return false go back to ask keypair name again
1292
+ def forj_check_cloud_keypair
1293
+ key_name = config[:keypair_name]
1294
+ return true if key_name.nil?
1295
+ config[:key_cloud_coherence] = false
1296
+ cloud_key = process_get(:keypairs, key_name)
1297
+ if !cloud_key.empty?
1298
+ if cloud_key[:coherent]
1299
+ config[:key_cloud_coherence] = true
1300
+ return true
1301
+ end
1302
+ else
1303
+ return true
1304
+ end
1305
+ keypair_display(cloud_key)
1306
+ s_ask = 'Do you still want to create new key?'
1307
+ PrcLib.fatal(1, 'This keypair name cannot be used. ' \
1308
+ 'You may check keypair_path setting ' \
1309
+ 'in your account.') unless agree(s_ask)
1310
+ false
1311
+ end
1312
+
1313
+ # pre process before asking keypair files
1314
+ # return true continue to ask keypair files
1315
+ # return false skip asking keypair files
1316
+ def forj_cloud_keypair_coherent?(_keypair_files)
1317
+ if config[:key_cloud_coherence]
1318
+ PrcLib.message('Your local ssh keypair is detected ' \
1319
+ 'and valid to access the box.')
1320
+ return false
1321
+ end
1322
+ true
1323
+ end
1125
1324
  end
1126
1325
 
1127
1326
  # Funtions for get
1128
1327
  class ForjCoreProcess
1129
1328
  def get_forge(sCloudObj, sForgeId, _hParams)
1130
1329
  s_query = {}
1131
- h_servers = []
1330
+ servers = {}
1132
1331
  s_query[:name] = sForgeId
1133
1332
 
1134
1333
  o_servers = process_query(:server, s_query)
@@ -1136,14 +1335,18 @@ class ForjCoreProcess
1136
1335
  regex = Regexp.new(format('\.%s$', sForgeId))
1137
1336
 
1138
1337
  o_servers.each do |o_server|
1139
- o_name = o_server[:name]
1140
- h_servers << o_server if regex =~ o_name
1338
+ name = o_server[:name]
1339
+ next unless regex =~ name
1340
+
1341
+ type = name.clone
1342
+ type['.' + sForgeId] = ''
1343
+ servers[type] = o_server
1141
1344
  end
1142
1345
  PrcLib.info('%s server(s) were found under instance name %s ',
1143
- h_servers.count, s_query[:name])
1346
+ servers.count, s_query[:name])
1144
1347
 
1145
- o_forge = register(h_servers, sCloudObj)
1146
- o_forge[:servers] = h_servers
1348
+ o_forge = register({}, sCloudObj)
1349
+ o_forge[:servers] = servers
1147
1350
  o_forge[:name] = sForgeId
1148
1351
  o_forge
1149
1352
  end
@@ -1154,14 +1357,14 @@ class ForjCoreProcess
1154
1357
  def delete_forge(_sCloudObj, hParams)
1155
1358
  PrcLib.state('Destroying server(s) of your forge')
1156
1359
 
1157
- forge_serverid = config.get(:forge_server)
1360
+ forge_serverid = hParams[:forge_server]
1158
1361
 
1159
1362
  o_forge = hParams[:forge]
1160
1363
 
1161
- o_forge[:servers].each do|server|
1364
+ o_forge[:servers].each do|_type, server|
1162
1365
  next if forge_serverid && forge_serverid != server[:id]
1163
1366
  register(server)
1164
- PrcLib.state("Destroying server '%s'", server[:name])
1367
+ PrcLib.state("Destroying server '%s - %s'", server[:name], server[:id])
1165
1368
  process_delete(:server)
1166
1369
  end
1167
1370
  if forge_serverid.nil?
@@ -1178,17 +1381,10 @@ end
1178
1381
  class ForjCoreProcess
1179
1382
  def ssh_connection(sObjectType, hParams)
1180
1383
  o_forge = hParams[:forge]
1181
- o_server = nil
1182
-
1183
- o_forge[:servers].each do|server|
1184
- next if hParams[:forge_server] != server[:id]
1185
- o_server = server
1186
- break
1187
- end
1188
1384
 
1189
1385
  # Get server information
1190
1386
  PrcLib.state('Getting server information')
1191
- o_server = process_get(:server, o_server[:id])
1387
+ o_server = o_forge[:servers, hParams[:forge_server]]
1192
1388
  register(o_server)
1193
1389
 
1194
1390
  public_ip = ssh_server_public_ip(o_server)
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: forj
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.7
4
+ version: 1.0.8
5
5
  platform: ruby
6
6
  authors:
7
7
  - forj team
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-03-23 00:00:00.000000000 Z
11
+ date: 2015-03-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: thor
@@ -142,14 +142,14 @@ dependencies:
142
142
  requirements:
143
143
  - - ~>
144
144
  - !ruby/object:Gem::Version
145
- version: 1.0.7
145
+ version: 1.0.8
146
146
  type: :runtime
147
147
  prerelease: false
148
148
  version_requirements: !ruby/object:Gem::Requirement
149
149
  requirements:
150
150
  - - ~>
151
151
  - !ruby/object:Gem::Version
152
- version: 1.0.7
152
+ version: 1.0.8
153
153
  - !ruby/object:Gem::Dependency
154
154
  name: rake
155
155
  requirement: !ruby/object:Gem::Requirement