forj 1.0.3 → 1.0.4
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.rubocop.yml +59 -0
- data/Gemfile +14 -15
- data/Rakefile +11 -3
- data/bin/forj +231 -338
- data/forj.gemspec +4 -7
- data/forj/defaults.yaml +3 -3
- data/lib/appinit.rb +21 -32
- data/lib/boot.rb +156 -0
- data/lib/cloud_connection.rb +42 -0
- data/lib/cloud_test.rb +86 -68
- data/lib/destroy.rb +97 -0
- data/lib/forj-settings.rb +350 -167
- data/lib/forj/ForjCli.rb +12 -14
- data/lib/forj/ForjCore.rb +78 -85
- data/lib/forj/process/ForjProcess.rb +1157 -771
- data/lib/get.rb +51 -0
- data/lib/ssh.rb +86 -78
- data/spec/boot_spec.rb +0 -1
- data/spec/spec_helper.rb +65 -65
- metadata +14 -22
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.
|
23
|
-
s.date = '
|
22
|
+
s.version = '1.0.4'
|
23
|
+
s.date = '2015-02-10'
|
24
24
|
s.summary = 'forj command line'
|
25
25
|
s.description = 'forj cli - See https://www.forj.io for documentation/information'
|
26
26
|
|
@@ -44,7 +44,7 @@ Gem::Specification.new do |s|
|
|
44
44
|
s.require_paths = %w[lib]
|
45
45
|
|
46
46
|
s.add_runtime_dependency 'thor', '>=0.16.0'
|
47
|
-
s.add_runtime_dependency 'fog', '1.
|
47
|
+
s.add_runtime_dependency 'fog', '~>1.26.0'
|
48
48
|
s.add_runtime_dependency 'git', '>=1.2.7'
|
49
49
|
s.add_runtime_dependency 'highline', '>= 1.6.21'
|
50
50
|
s.add_runtime_dependency 'ansi', '>= 1.4.3'
|
@@ -52,13 +52,10 @@ 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', '~> 0.2
|
55
|
+
s.add_runtime_dependency 'lorj', '~> 1.0.2'
|
56
56
|
|
57
|
-
s.add_development_dependency "bundler"
|
58
57
|
s.add_development_dependency "rake", "~> 10.0"
|
59
58
|
s.add_development_dependency "rspec", "~> 3.1.0"
|
60
59
|
s.rdoc_options << '--title' << 'Lorj - The Process Controllers framework system' <<
|
61
60
|
'--main' << 'README.md'
|
62
|
-
|
63
|
-
|
64
61
|
end
|
data/forj/defaults.yaml
CHANGED
@@ -184,19 +184,19 @@
|
|
184
184
|
:desc: "Domain name added to each hosts."
|
185
185
|
:account_exclusive: true
|
186
186
|
:account: true
|
187
|
-
:post_step_function: :
|
187
|
+
:post_step_function: :forj_dns_settings
|
188
188
|
:ask_step: 3
|
189
189
|
:dns_service:
|
190
190
|
:desc: "DNS service region name Maestro will use."
|
191
191
|
:account_exclusive: true
|
192
192
|
:account: true
|
193
|
-
:pre_step_function: :
|
193
|
+
:pre_step_function: :forj_dns_settings?
|
194
194
|
:ask_step: 3
|
195
195
|
:dns_tenant_id:
|
196
196
|
:desc: "DNS Tenant ID Maestro will use"
|
197
197
|
:account_exclusive: true
|
198
198
|
:account: true
|
199
|
-
:pre_step_function: :
|
199
|
+
:pre_step_function: :forj_dns_settings?
|
200
200
|
:ask_step: 3
|
201
201
|
|
202
202
|
:maestro:
|
data/lib/appinit.rb
CHANGED
@@ -14,39 +14,28 @@
|
|
14
14
|
# See the License for the specific language governing permissions and
|
15
15
|
# limitations under the License.
|
16
16
|
|
17
|
-
|
18
|
-
require 'lorj'
|
19
|
-
|
20
17
|
# Module to initialize the application
|
21
18
|
# TODO: Cleanup about Global variables used. Should be replaced by PrcLib
|
22
19
|
# or other kind of setting.
|
23
|
-
module
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
AppInit.ensure_dir_exists($FORJ_CREDS_PATH)
|
45
|
-
end
|
46
|
-
|
47
|
-
def AppInit.ensure_dir_exists(path)
|
48
|
-
if not PrcLib.dir_exists?(path)
|
49
|
-
FileUtils.mkpath(path) if not File.directory?(path)
|
50
|
-
end
|
51
|
-
end
|
20
|
+
module Forj
|
21
|
+
class << self
|
22
|
+
attr_accessor :build_path, :keypairs_path
|
23
|
+
end
|
24
|
+
|
25
|
+
module_function
|
26
|
+
|
27
|
+
def keypairs_path=(v)
|
28
|
+
@keypairs_path = File.expand_path(v) unless @keypairs_path
|
29
|
+
PrcLib.ensure_dir_exists(@keypairs_path)
|
30
|
+
begin
|
31
|
+
FileUtils.chmod(0700, @keypairs_path) # no-op on windows
|
32
|
+
rescue => e
|
33
|
+
fatal_error(1, e.message)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
def build_path=(v)
|
38
|
+
@build_path = File.expand_path(v) unless @build_path
|
39
|
+
PrcLib.ensure_dir_exists(@build_path)
|
40
|
+
end
|
52
41
|
end
|
data/lib/boot.rb
ADDED
@@ -0,0 +1,156 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
# encoding: UTF-8
|
3
|
+
|
4
|
+
# (c) Copyright 2014 Hewlett-Packard Development Company, L.P.
|
5
|
+
#
|
6
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
7
|
+
# you may not use this file except in compliance with the License.
|
8
|
+
# You may obtain a copy of the License at
|
9
|
+
#
|
10
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
11
|
+
#
|
12
|
+
# Unless required by applicable law or agreed to in writing, software
|
13
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
14
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
15
|
+
# See the License for the specific language governing permissions and
|
16
|
+
# limitations under the License.
|
17
|
+
|
18
|
+
require 'highline/import'
|
19
|
+
require 'cloud_connection.rb'
|
20
|
+
#
|
21
|
+
# Boot module
|
22
|
+
#
|
23
|
+
module Forj
|
24
|
+
# This module provides the behavior to boot your forge
|
25
|
+
module Boot
|
26
|
+
@account = nil
|
27
|
+
attr_accessor :account
|
28
|
+
|
29
|
+
def self.deprecated_name?(blueprint, on_or_name,
|
30
|
+
old_accountname, as,
|
31
|
+
old_name
|
32
|
+
)
|
33
|
+
# depreciated: <BluePrint> on <AccountName> as <InstanceName>
|
34
|
+
if old_accountname && as && old_name
|
35
|
+
msg = format(
|
36
|
+
"The syntax `forj boot '%s' on '%s' as '%s'`" \
|
37
|
+
" is depreciated. \nUse `forj boot '%s' '%s' ",
|
38
|
+
blueprint, old_accountname, old_name, blueprint, old_name
|
39
|
+
)
|
40
|
+
|
41
|
+
if account.get('account_name') == old_accountname
|
42
|
+
PrcLib.warning('%s` instead.', msg)
|
43
|
+
else
|
44
|
+
PrcLib.warning("%s -a '%s'` instead.", msg, old_accountname)
|
45
|
+
end
|
46
|
+
name = old_name
|
47
|
+
@account.set(:account_name, old_accountname)
|
48
|
+
else
|
49
|
+
name = on_or_name
|
50
|
+
end
|
51
|
+
name
|
52
|
+
end
|
53
|
+
|
54
|
+
def self.load_options(options, options_map)
|
55
|
+
options_map.each do |opt_key, ac_key|
|
56
|
+
unless options[opt_key].nil?
|
57
|
+
value = yield(opt_key, options[opt_key])
|
58
|
+
@account.set(ac_key, options[opt_key]) unless value.nil?
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
def self.validate_keypath(options)
|
64
|
+
if options[:key_path]
|
65
|
+
m_found = options[:key_path].match(/^(.*)(\.pub)?$/)
|
66
|
+
if m_found
|
67
|
+
key_path = File.expand_path(m_found[1])
|
68
|
+
if m_found[2] && !(File.exist?(
|
69
|
+
File.expand_path(m_found[1] + m_found[2])
|
70
|
+
))
|
71
|
+
PrcLib.fatal(
|
72
|
+
1,
|
73
|
+
"'%s' is not a valid keypair files." \
|
74
|
+
' At least the public key (.pub) is have to exist.',
|
75
|
+
key_path
|
76
|
+
)
|
77
|
+
end
|
78
|
+
@account.set(:keypair_path, key_path)
|
79
|
+
else
|
80
|
+
PrcLib.fatal(
|
81
|
+
1,
|
82
|
+
"'%s' is not a valid keypair files." \
|
83
|
+
'At least the public key (.pub) is have to exist.',
|
84
|
+
key_path
|
85
|
+
)
|
86
|
+
end
|
87
|
+
end
|
88
|
+
end
|
89
|
+
|
90
|
+
def self.install_blueprint?(blueprint, name)
|
91
|
+
@account[:instance_name] = name
|
92
|
+
|
93
|
+
if blueprint == 'maestro'
|
94
|
+
PrcLib.info("Starting boot process of '%s'. No blueprint requested.",
|
95
|
+
@account[:instance_name])
|
96
|
+
else
|
97
|
+
@account[:blueprint] = blueprint
|
98
|
+
PrcLib.info("Starting boot process of '%s' with blueprint '%s'.",
|
99
|
+
@account[:instance_name], @account[:blueprint])
|
100
|
+
end
|
101
|
+
end
|
102
|
+
|
103
|
+
def self.boot(blueprint, on_or_name, deprecated_name, options)
|
104
|
+
@account = Lorj::Account.new(options[:config])
|
105
|
+
|
106
|
+
name = deprecated_name?(blueprint, on_or_name, deprecated_name[0],
|
107
|
+
deprecated_name[1], deprecated_name[2])
|
108
|
+
|
109
|
+
PrcLib.fatal(1, "instance name '%s' not supported. Support only lower" \
|
110
|
+
' case, numeric and dash caracters.',
|
111
|
+
name) unless /^[\d[[:lower:]]-]+$/ =~ name
|
112
|
+
|
113
|
+
# Options are added if they are set.
|
114
|
+
# Otherwise, get will retrieve the default value.
|
115
|
+
|
116
|
+
@account[:account_name] = options[:account_name] if options[:account_name]
|
117
|
+
|
118
|
+
@account.ac_load @account[:account_name]
|
119
|
+
|
120
|
+
options_map = { :infra => :infra_repo, :key_name => :keypair_name,
|
121
|
+
:key_path => :keypair_path,
|
122
|
+
:security_group => :security_group,
|
123
|
+
:image_name => :image_name, :maestro_flavor => :flavor,
|
124
|
+
:bp_flavor => :bp_flavor, :maestro_repo => :maestro_repo,
|
125
|
+
:branch => :branch, :test_box => :test_box }
|
126
|
+
|
127
|
+
load_options(options, options_map) do |key, value|
|
128
|
+
case key
|
129
|
+
when :test_box
|
130
|
+
path = File.expand_path(value)
|
131
|
+
return path if File.directory?(path)
|
132
|
+
return nil
|
133
|
+
end
|
134
|
+
value
|
135
|
+
end
|
136
|
+
|
137
|
+
PrcLib.warning(
|
138
|
+
'test_box is currently disabled in this version.' \
|
139
|
+
'It will be re-activated in newer version.'
|
140
|
+
) if options[:test_box]
|
141
|
+
|
142
|
+
validate_keypath(options)
|
143
|
+
|
144
|
+
# o_cloud = get_o_cloud(o_forj_account)
|
145
|
+
o_cloud = Forj::CloudConnection.connect(@account)
|
146
|
+
|
147
|
+
install_blueprint?(blueprint, name)
|
148
|
+
PrcLib.high_level_msg("Preparing your forge '%s'.Please be patient. "\
|
149
|
+
"more output in '%s'\n",
|
150
|
+
@account[:instance_name],
|
151
|
+
PrcLib.log_file)
|
152
|
+
|
153
|
+
o_cloud.create(:forge)
|
154
|
+
end
|
155
|
+
end
|
156
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
# encoding: UTF-8
|
3
|
+
|
4
|
+
# (c) Copyright 2014 Hewlett-Packard Development Company, L.P.
|
5
|
+
#
|
6
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
7
|
+
# you may not use this file except in compliance with the License.
|
8
|
+
# You may obtain a copy of the License at
|
9
|
+
#
|
10
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
11
|
+
#
|
12
|
+
# Unless required by applicable law or agreed to in writing, software
|
13
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
14
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
15
|
+
# See the License for the specific language governing permissions and
|
16
|
+
# limitations under the License.
|
17
|
+
|
18
|
+
module Forj
|
19
|
+
# Provide cloud object
|
20
|
+
module CloudConnection
|
21
|
+
def self.connect(account)
|
22
|
+
a_processes = []
|
23
|
+
|
24
|
+
# Defines how to manage Maestro and forges
|
25
|
+
# create a maestro box. Identify a forge instance, delete it,...
|
26
|
+
a_processes << File.join(LIB_PATH, 'forj', 'ForjCore.rb')
|
27
|
+
|
28
|
+
# Defines how cli will control FORJ features
|
29
|
+
# boot/down/ssh/...
|
30
|
+
a_processes << File.join(LIB_PATH, 'forj', 'ForjCli.rb')
|
31
|
+
|
32
|
+
# Loading CloudCore embedding provider controller + its process.
|
33
|
+
o_cloud = Lorj::CloudCore.new(
|
34
|
+
account,
|
35
|
+
account[:account_name],
|
36
|
+
a_processes
|
37
|
+
)
|
38
|
+
|
39
|
+
o_cloud
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
data/lib/cloud_test.rb
CHANGED
@@ -1,121 +1,139 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
2
|
|
3
|
-
#require 'byebug'
|
3
|
+
# require 'byebug'
|
4
4
|
|
5
|
-
|
6
|
-
|
5
|
+
APP_PATH = File.dirname(__FILE__)
|
6
|
+
LIB_PATH = File.expand_path(File.join(File.dirname(APP_PATH), 'lib'))
|
7
7
|
|
8
|
-
|
8
|
+
LOAD_PATH << LIB_PATH
|
9
9
|
|
10
|
-
|
10
|
+
LOAD_PATH << File.join(LIB_PATH, 'lib-forj', 'lib')
|
11
11
|
|
12
12
|
require 'appinit.rb'
|
13
13
|
|
14
14
|
# Initialize forj paths
|
15
|
-
AppInit
|
15
|
+
AppInit.forj_initialize
|
16
16
|
|
17
17
|
# Initialize global Log object
|
18
|
-
|
18
|
+
FORJ_LOGGER = ForjLog.new
|
19
19
|
|
20
20
|
require 'lib-forj.rb'
|
21
21
|
|
22
22
|
Logging.set_level(Logger::DEBUG)
|
23
23
|
|
24
24
|
# Load global Config
|
25
|
-
|
25
|
+
o_config = ForjConfig.new
|
26
26
|
|
27
|
-
|
27
|
+
a_processes = []
|
28
28
|
|
29
29
|
# Defines how to manage Maestro and forges
|
30
30
|
# create a maestro box. Identify a forge instance, delete it,...
|
31
|
-
|
31
|
+
a_processes << File.join(LIB_PATH, 'forj', 'ForjCore.rb')
|
32
32
|
|
33
33
|
# Defines how cli will control FORJ features
|
34
34
|
# boot/down/ssh/...
|
35
|
-
|
35
|
+
a_processes << File.join(LIB_PATH, 'forj', 'ForjCli.rb')
|
36
36
|
|
37
|
-
|
37
|
+
# PrcLib.core_level = 3 # verbose
|
38
38
|
|
39
|
-
infra_dir = File.expand_path(
|
39
|
+
infra_dir = File.expand_path(o_config.get(:infra_repo))
|
40
40
|
|
41
41
|
# Ask information if needed.
|
42
|
-
|
43
|
-
|
42
|
+
unless Dir.exist?(File.expand_path(infra_dir))
|
43
|
+
Logging.warning(<<-END
|
44
44
|
Your infra workspace directory is missing.
|
45
45
|
|
46
|
-
Forj uses an infra workspace directory to store any kind of data that are
|
47
|
-
|
48
|
-
|
46
|
+
Forj uses an infra workspace directory to store any kind of data that are
|
47
|
+
private to you.
|
48
|
+
We provides ways to send those data securily to your new Forge instance,
|
49
|
+
as metadata.
|
50
|
+
In production case, we suggest you to keep it safe in your SCM preferred
|
51
|
+
database.
|
49
52
|
|
50
|
-
If you already have an existing infra workspace,
|
53
|
+
If you already have an existing infra workspace,
|
54
|
+
use 'forj set infra_repo=<PathToYourRepo>' to set it and restart.
|
51
55
|
|
52
|
-
Otherwise, we will build a new one with some predefined data,
|
56
|
+
Otherwise, we will build a new one with some predefined data,
|
57
|
+
you can review and update later.
|
53
58
|
END
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
59
|
+
)
|
60
|
+
s_ask = format(
|
61
|
+
'Do you want to create a new one from Maestro (yes/no)?',
|
62
|
+
infra_dir
|
63
|
+
)
|
64
|
+
b_build_infra = agree(s_ask)
|
65
|
+
unless b_build_infra
|
66
|
+
puts 'Process aborted on your demand.'
|
67
|
+
exit 0
|
68
|
+
end
|
61
69
|
end
|
62
70
|
|
63
|
-
|
64
|
-
|
65
|
-
#oConfig.set(:instance_name, "test")
|
66
|
-
#oCloud.Create(:metadata)
|
67
|
-
#oCloud.Create(:infra_repository)
|
68
|
-
#oCloud.Create(:userdata)
|
71
|
+
o_cloud = ForjCloud.new(o_config, 'hpcloud', a_processes)
|
69
72
|
|
73
|
+
# o_config.set(:instance_name, "test")
|
74
|
+
# o_cloud.Create(:metadata)
|
75
|
+
# o_cloud.Create(:infra_repository)
|
76
|
+
# o_cloud.Create(:userdata)
|
70
77
|
|
71
|
-
#
|
72
|
-
#
|
78
|
+
# o_cloud.Setup(:server, 'hpcloud')
|
79
|
+
# o_cloud.Setup(:forge, 'hpcloud')
|
73
80
|
|
74
|
-
#
|
81
|
+
# o_cloud.Create(:forge)
|
75
82
|
|
76
|
-
#
|
77
|
-
#
|
83
|
+
# o_config.set(:instance_name, 'servertestluis')
|
84
|
+
# o_cloud.Create(:forge)
|
78
85
|
|
79
|
-
|
86
|
+
o_forge = o_cloud.Get(:forge, 'luistest')
|
80
87
|
|
81
|
-
#Ask the user to get server(s) to destroy
|
88
|
+
# Ask the user to get server(s) to destroy
|
82
89
|
server_id_length = 0
|
83
90
|
server_name_length = 0
|
84
91
|
|
85
|
-
|
86
|
-
if server[:id].length
|
87
|
-
server_id_length = server[:id].length
|
92
|
+
o_forge[:server].each do |server|
|
93
|
+
if server[:id].length > server_id_length
|
94
|
+
server_id_length = server[:id].length
|
88
95
|
end
|
89
96
|
|
90
|
-
if server[:name].length
|
91
|
-
server_name_length = server[:name].length
|
97
|
+
if server[:name].length > server_name_length
|
98
|
+
server_name_length = server[:name].length
|
92
99
|
end
|
93
|
-
|
100
|
+
end
|
94
101
|
|
95
102
|
server_index = 1
|
96
|
-
#Display headers
|
97
|
-
puts
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
103
|
+
# Display headers
|
104
|
+
puts format(
|
105
|
+
'|%s |%s |%s |',
|
106
|
+
'Index '.ljust(6),
|
107
|
+
'Name'.ljust(server_name_length),
|
108
|
+
'ID'.ljust(server_id_length)
|
109
|
+
)
|
110
|
+
# Display Forge servers detail
|
111
|
+
o_forge[:server].each do |server|
|
112
|
+
puts format(
|
113
|
+
'|%s |%s |%s |',
|
114
|
+
server_index.to_s.ljust(6),
|
115
|
+
server[:name].to_s.ljust(server_name_length),
|
116
|
+
server[:id].to_s.ljust(server_id_length)
|
117
|
+
)
|
118
|
+
server_index += 1
|
110
119
|
end
|
111
120
|
|
121
|
+
o_high_line = HighLine.new
|
122
|
+
|
123
|
+
index = o_high_line.ask(
|
124
|
+
'Select the index of the server to create the ssh connection',
|
125
|
+
Integer
|
126
|
+
) do |q|
|
127
|
+
q.below = o_forge[:server].count + 1
|
128
|
+
q.above = 0
|
129
|
+
end
|
112
130
|
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
#
|
117
|
-
#
|
118
|
-
#
|
119
|
-
|
131
|
+
o_config.set(:instance_name, 'luistest')
|
132
|
+
o_config.set(:forge_server, o_forge[:server][index - 1][:id])
|
133
|
+
o_config.set(:server_name, o_forge[:server][index - 1][:name])
|
134
|
+
# o_config.set(:box, 'maestro')
|
135
|
+
# o_config.set(:instance_name, 'luistest')
|
136
|
+
# o_config.Create(:server)
|
137
|
+
o_cloud.Create(:ssh)
|
120
138
|
|
121
|
-
#
|
139
|
+
# o_cloud.Query(:server, 'maestro')
|