qingcloud-sdk 0.4.1 → 2.0.0.pre.alpha.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (46) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE +201 -21
  3. data/README.md +141 -61
  4. data/bin/console +3 -3
  5. data/lib/qingcloud/sdk.rb +16 -14
  6. data/lib/qingcloud/sdk/general/config.rb +70 -0
  7. data/lib/qingcloud/sdk/general/contract.rb +28 -17
  8. data/lib/qingcloud/sdk/general/default/config.yaml +13 -0
  9. data/lib/qingcloud/sdk/general/error.rb +41 -32
  10. data/lib/qingcloud/sdk/general/logger.rb +54 -0
  11. data/lib/qingcloud/sdk/request/preprocessor.rb +81 -0
  12. data/lib/qingcloud/sdk/request/request.rb +80 -0
  13. data/lib/qingcloud/sdk/request/signer.rb +53 -0
  14. data/lib/qingcloud/sdk/service/cache.rb +1005 -0
  15. data/lib/qingcloud/sdk/service/dns_alias.rb +150 -0
  16. data/lib/qingcloud/sdk/service/eip.rb +389 -0
  17. data/lib/qingcloud/sdk/service/image.rb +304 -0
  18. data/lib/qingcloud/sdk/service/instance.rb +585 -0
  19. data/lib/qingcloud/sdk/service/job.rb +71 -0
  20. data/lib/qingcloud/sdk/service/key_pair.rb +257 -0
  21. data/lib/qingcloud/sdk/service/load_balancer.rb +1119 -0
  22. data/lib/qingcloud/sdk/service/mongo.rb +566 -0
  23. data/lib/qingcloud/sdk/service/qingcloud.rb +185 -0
  24. data/lib/qingcloud/sdk/service/rdb.rb +751 -0
  25. data/lib/qingcloud/sdk/service/router.rb +778 -0
  26. data/lib/qingcloud/sdk/service/security_group.rb +645 -0
  27. data/lib/qingcloud/sdk/service/shared_storage.rb +666 -0
  28. data/lib/qingcloud/sdk/service/snapshot.rb +283 -0
  29. data/lib/qingcloud/sdk/service/tag.rb +227 -0
  30. data/lib/qingcloud/sdk/service/user_data.rb +61 -0
  31. data/lib/qingcloud/sdk/service/volume.rb +296 -0
  32. data/lib/qingcloud/sdk/service/vxnet.rb +295 -0
  33. data/lib/qingcloud/sdk/version.rb +19 -5
  34. metadata +98 -29
  35. data/.gitignore +0 -13
  36. data/.rspec +0 -2
  37. data/.travis.yml +0 -3
  38. data/Rakefile +0 -6
  39. data/lib/qingcloud/sdk/iaas/connector.rb +0 -99
  40. data/lib/qingcloud/sdk/iaas/foundation.rb +0 -73
  41. data/lib/qingcloud/sdk/iaas/service.rb +0 -1274
  42. data/lib/qingcloud/sdk/template/config.json +0 -4
  43. data/lib/qingcloud/sdk/utility/file_manager.rb +0 -43
  44. data/lib/qingcloud/sdk/utility/json_parser.rb +0 -41
  45. data/lib/qingcloud/sdk/utility/logger.rb +0 -19
  46. data/qingcloud-sdk.gemspec +0 -31
data/bin/console CHANGED
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env ruby
2
2
 
3
- require "bundler/setup"
4
- require "qingcloud/sdk"
3
+ require 'bundler/setup'
4
+ require 'qingcloud/sdk'
5
5
 
6
6
  # You can add fixtures and/or initialization code here to make experimenting
7
7
  # with your gem easier. You can also use a different console, if you like.
@@ -10,5 +10,5 @@ require "qingcloud/sdk"
10
10
  # require "pry"
11
11
  # Pry.start
12
12
 
13
- require "irb"
13
+ require 'irb'
14
14
  IRB.start
data/lib/qingcloud/sdk.rb CHANGED
@@ -1,15 +1,17 @@
1
- require 'qingcloud/sdk/version'
1
+ # +-------------------------------------------------------------------------
2
+ # | Copyright (C) 2016 Yunify, Inc.
3
+ # +-------------------------------------------------------------------------
4
+ # | Licensed under the Apache License, Version 2.0 (the "License");
5
+ # | you may not use this work except in compliance with the License.
6
+ # | You may obtain a copy of the License in the LICENSE file, or at:
7
+ # |
8
+ # | http://www.apache.org/licenses/LICENSE-2.0
9
+ # |
10
+ # | Unless required by applicable law or agreed to in writing, software
11
+ # | distributed under the License is distributed on an "AS IS" BASIS,
12
+ # | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # | See the License for the specific language governing permissions and
14
+ # | limitations under the License.
15
+ # +-------------------------------------------------------------------------
2
16
 
3
- # General
4
- require 'qingcloud/sdk/general/contract'
5
- require 'qingcloud/sdk/general/error'
6
-
7
- # Utility
8
- require 'qingcloud/sdk/utility/logger'
9
- require 'qingcloud/sdk/utility/file_manager'
10
- require 'qingcloud/sdk/utility/json_parser'
11
-
12
- # Client
13
- require 'qingcloud/sdk/iaas/connector'
14
- require 'qingcloud/sdk/iaas/foundation'
15
- require 'qingcloud/sdk/iaas/service'
17
+ Dir[File.dirname(__FILE__) + '/sdk/**/*.rb'].each { |file| require file }
@@ -0,0 +1,70 @@
1
+ # +-------------------------------------------------------------------------
2
+ # | Copyright (C) 2016 Yunify, Inc.
3
+ # +-------------------------------------------------------------------------
4
+ # | Licensed under the Apache License, Version 2.0 (the "License");
5
+ # | you may not use this work except in compliance with the License.
6
+ # | You may obtain a copy of the License in the LICENSE file, or at:
7
+ # |
8
+ # | http://www.apache.org/licenses/LICENSE-2.0
9
+ # |
10
+ # | Unless required by applicable law or agreed to in writing, software
11
+ # | distributed under the License is distributed on an "AS IS" BASIS,
12
+ # | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # | See the License for the specific language governing permissions and
14
+ # | limitations under the License.
15
+ # +-------------------------------------------------------------------------
16
+
17
+ require 'fileutils'
18
+ require 'yaml'
19
+
20
+ require 'active_support/core_ext/hash/keys'
21
+ require 'active_support/core_ext/hash/deep_merge'
22
+ require 'net/http/persistent'
23
+
24
+ module QingCloud
25
+ module SDK
26
+ class Config < Hash
27
+ attr_accessor :connection
28
+
29
+ def self.init(access_key_id, secret_access_key)
30
+ initial_config = {
31
+ qy_access_key_id: access_key_id,
32
+ qy_secret_access_key: secret_access_key,
33
+ }
34
+ Config.new(initial_config)
35
+ end
36
+
37
+ def initialize(initial_config = {})
38
+ self.connection = Net::HTTP::Persistent.new
39
+ load_default_config
40
+ update initial_config
41
+ end
42
+
43
+ def update(another_config = {})
44
+ deep_merge! another_config.deep_symbolize_keys!
45
+ Logger.set_level self[:log_level]
46
+ self
47
+ end
48
+
49
+ def load_default_config
50
+ load_config_from_file Contract::DEFAULT_CONFIG_FILEPATH
51
+ end
52
+
53
+ def load_user_config
54
+ install_default_user_config unless File.exist? Contract::USER_CONFIG_FILEPATH
55
+ load_config_from_file Contract::USER_CONFIG_FILEPATH
56
+ end
57
+
58
+ def load_config_from_file(path)
59
+ path = path.sub '~', Dir.home if path.start_with? '~/'
60
+ update YAML.load_file File.absolute_path path
61
+ end
62
+
63
+ def install_default_user_config
64
+ Logger.warn "Installing default config file to #{Contract::USER_CONFIG_FILEPATH}"
65
+ FileUtils.mkdir_p Contract::USER_SUPPORT_DIRECTORY
66
+ FileUtils.copy Contract::DEFAULT_CONFIG_FILEPATH, Contract::USER_CONFIG_FILEPATH
67
+ end
68
+ end
69
+ end
70
+ end
@@ -1,20 +1,31 @@
1
- module QingCloud
2
- module SDK
3
- module Contract
4
-
5
- SUPPORT_DIRECTORY = "#{Dir.home}/.qingcloud"
6
- CONFIG_FILE_NAME = 'config.json'
7
- CONFIG_FILE_PATH = "#{SUPPORT_DIRECTORY}/#{CONFIG_FILE_NAME}"
8
- LOG_FILE_NAME = 'access.log'
9
- LOG_FILE_PATH = "#{SUPPORT_DIRECTORY}/#{LOG_FILE_NAME}"
1
+ # +-------------------------------------------------------------------------
2
+ # | Copyright (C) 2016 Yunify, Inc.
3
+ # +-------------------------------------------------------------------------
4
+ # | Licensed under the Apache License, Version 2.0 (the "License");
5
+ # | you may not use this work except in compliance with the License.
6
+ # | You may obtain a copy of the License in the LICENSE file, or at:
7
+ # |
8
+ # | http://www.apache.org/licenses/LICENSE-2.0
9
+ # |
10
+ # | Unless required by applicable law or agreed to in writing, software
11
+ # | distributed under the License is distributed on an "AS IS" BASIS,
12
+ # | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # | See the License for the specific language governing permissions and
14
+ # | limitations under the License.
15
+ # +-------------------------------------------------------------------------
10
16
 
11
- TEMPLATE_DIRECTORY = Gem::Specification.find_by_name('qingcloud-sdk').gem_dir + '/lib/qingcloud/sdk/template'
12
- TEMPLATE_CONFIG_FILE_NAME = 'config.json'
13
- TEMPLATE_CONFIG_FILE_PATH = "#{TEMPLATE_DIRECTORY}/#{TEMPLATE_CONFIG_FILE_NAME}"
14
-
15
- API_URL = 'https://api.qingcloud.com'
16
- IaaS_API_URL = "#{API_URL}/iaas/?"
17
+ module QingCloud
18
+ module SDK
19
+ module Contract
20
+ USER_SUPPORT_DIRECTORY = "#{Dir.home}/.qingcloud".freeze
21
+ USER_CONFIG_FILENAME = 'config.yaml'.freeze
22
+ USER_CONFIG_FILEPATH = "#{USER_SUPPORT_DIRECTORY}/#{USER_CONFIG_FILENAME}".freeze
17
23
 
18
- end
24
+ # GEM_DIRECTORY = Gem::Specification.find_by_name('qingcloud-sdk').gem_dir
25
+ # DEFAULT_SUPPORT_DIRECTORY = GEM_DIRECTORY + '/lib/qingcloud/sdk/commons/default'
26
+ DEFAULT_SUPPORT_DIRECTORY = File.expand_path(File.dirname(__FILE__) + '/./default')
27
+ DEFAULT_CONFIG_FILENAME = 'config.yaml'.freeze
28
+ DEFAULT_CONFIG_FILEPATH = "#{DEFAULT_SUPPORT_DIRECTORY}/#{DEFAULT_CONFIG_FILENAME}".freeze
19
29
  end
20
- end
30
+ end
31
+ end
@@ -0,0 +1,13 @@
1
+ # QingCloud services configuration
2
+
3
+ #qy_access_key_id: 'ACCESS_KEY_ID'
4
+ #qy_secret_access_key: 'SECRET_ACCESS_KEY'
5
+
6
+ host: 'api.qingcloud.com'
7
+ port: 443
8
+ protocol: 'https'
9
+ uri: '/iaas'
10
+ connection_retries: 3
11
+
12
+ # Valid log levels are "debug", "info", "warn", "error", and "fatal".
13
+ log_level: 'warn'
@@ -1,39 +1,48 @@
1
- module QingCloud
2
- module SDK
3
- module Error
1
+ # +-------------------------------------------------------------------------
2
+ # | Copyright (C) 2016 Yunify, Inc.
3
+ # +-------------------------------------------------------------------------
4
+ # | Licensed under the Apache License, Version 2.0 (the "License");
5
+ # | you may not use this work except in compliance with the License.
6
+ # | You may obtain a copy of the License in the LICENSE file, or at:
7
+ # |
8
+ # | http://www.apache.org/licenses/LICENSE-2.0
9
+ # |
10
+ # | Unless required by applicable law or agreed to in writing, software
11
+ # | distributed under the License is distributed on an "AS IS" BASIS,
12
+ # | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # | See the License for the specific language governing permissions and
14
+ # | limitations under the License.
15
+ # +-------------------------------------------------------------------------
4
16
 
5
- class SDKError < StandardError
6
- end
17
+ module QingCloud
18
+ module SDK
19
+ class SDKError < StandardError
20
+ end
7
21
 
8
- class NetworkError < SDKError
9
- def message
10
- 'Network Error, please check your internet connection.'
11
- end
12
- end
22
+ class NetworkError < SDKError
23
+ end
13
24
 
14
- class ServerError < SDKError
15
- def initialize(code)
16
- super "Server Response with Error Code \"#{code}\"."
17
- end
18
- end
25
+ class ParameterRequiredError < SDKError
26
+ def initialize(parameter_name, parent_name)
27
+ @parameter_name = parameter_name
28
+ @parent_name = parent_name
29
+ end
19
30
 
20
- class ParameterError < SDKError
21
- def initialize(something)
22
- super "Parameter Error when \"#{something}\"."
23
- end
24
- end
31
+ def message
32
+ "\"#{@parameter_name}\" is required in \"#{@parent_name}\"."
33
+ end
34
+ end
25
35
 
26
- class APIError < SDKError
27
- def initialize(something)
28
- super "API Error: \"#{something}\"."
29
- end
30
- end
36
+ class ParameterValueNotAllowedError < SDKError
37
+ def initialize(parameter_name, parameter_value, allowed_values)
38
+ @parameter_name = parameter_name
39
+ @parameter_value = parameter_value
40
+ @allowed_values = allowed_values
41
+ end
31
42
 
32
- class AnalyseError < SDKError
33
- def initialize(something)
34
- super "Analyse Error when \"#{something}\"."
35
- end
36
- end
37
- end
43
+ def message
44
+ "\"#{@parameter_name}\" value \"#{@parameter_value}\" is not allowed, should be one of #{@allowed_values.join ', '}."
45
+ end
38
46
  end
39
- end
47
+ end
48
+ end
@@ -0,0 +1,54 @@
1
+ # +-------------------------------------------------------------------------
2
+ # | Copyright (C) 2016 Yunify, Inc.
3
+ # +-------------------------------------------------------------------------
4
+ # | Licensed under the Apache License, Version 2.0 (the "License");
5
+ # | you may not use this work except in compliance with the License.
6
+ # | You may obtain a copy of the License in the LICENSE file, or at:
7
+ # |
8
+ # | http://www.apache.org/licenses/LICENSE-2.0
9
+ # |
10
+ # | Unless required by applicable law or agreed to in writing, software
11
+ # | distributed under the License is distributed on an "AS IS" BASIS,
12
+ # | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # | See the License for the specific language governing permissions and
14
+ # | limitations under the License.
15
+ # +-------------------------------------------------------------------------
16
+
17
+ require 'active_support/logger'
18
+
19
+ module QingCloud
20
+ module SDK
21
+ class Logger
22
+ @@logger = ActiveSupport::Logger.new STDOUT
23
+ @@level = :warn
24
+
25
+ def self.set_level(level)
26
+ index = %w(debug info warn error fatal).find_index level.to_s
27
+ @@logger.level = index.nil? ? 0 : index
28
+ @@level = level.to_sym
29
+ end
30
+
31
+ set_level :warn
32
+
33
+ def self.debug(text)
34
+ @@logger.debug text
35
+ end
36
+
37
+ def self.info(text)
38
+ @@logger.info text
39
+ end
40
+
41
+ def self.warn(text)
42
+ @@logger.warn text
43
+ end
44
+
45
+ def self.error(text)
46
+ @@logger.error text
47
+ end
48
+
49
+ def self.fatal(text)
50
+ @@logger.fatal text
51
+ end
52
+ end
53
+ end
54
+ end
@@ -0,0 +1,81 @@
1
+ # +-------------------------------------------------------------------------
2
+ # | Copyright (C) 2016 Yunify, Inc.
3
+ # +-------------------------------------------------------------------------
4
+ # | Licensed under the Apache License, Version 2.0 (the "License");
5
+ # | you may not use this work except in compliance with the License.
6
+ # | You may obtain a copy of the License in the LICENSE file, or at:
7
+ # |
8
+ # | http://www.apache.org/licenses/LICENSE-2.0
9
+ # |
10
+ # | Unless required by applicable law or agreed to in writing, software
11
+ # | distributed under the License is distributed on an "AS IS" BASIS,
12
+ # | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # | See the License for the specific language governing permissions and
14
+ # | limitations under the License.
15
+ # +-------------------------------------------------------------------------
16
+
17
+ require 'active_support/core_ext/hash/keys'
18
+
19
+ module QingCloud
20
+ module SDK
21
+ class Preprocessor
22
+ def self.do(input)
23
+ input = decorate_input input
24
+
25
+ config = input[:config]
26
+ input[:request_endpoint] = "#{config[:protocol]}://#{config[:host]}:#{config[:port]}"
27
+
28
+ parsed_params = {}
29
+ input[:request_params].each do |param_k, param_v|
30
+ if param_v.is_a? Array
31
+ param_v.each_with_index do |value, index|
32
+ if value.is_a? Hash
33
+ value.each do |value_k, value_v|
34
+ parsed_params["#{param_k}.#{index}.#{value_k}"] = value_v
35
+ end
36
+ else
37
+ parsed_params["#{param_k}.#{index}"] = value
38
+ end
39
+ end
40
+ elsif param_v.is_a? Hash
41
+ param_v.each do |key, value|
42
+ parsed_params["#{param_k}.#{key}"] = value
43
+ end
44
+ else
45
+ parsed_params[param_k] = param_v
46
+ end
47
+ end
48
+ input[:request_params] = parsed_params.deep_symbolize_keys!
49
+ input[:request_params].update(
50
+ action: input[:api_name],
51
+ time_stamp: Time.now.utc.strftime('%Y-%m-%dT%H:%M:%SZ'),
52
+ version: 1,
53
+ signature_method: 'HmacSHA256',
54
+ signature_version: 1,
55
+ access_key_id: input[:config][:qy_access_key_id],
56
+ )
57
+
58
+ if input[:properties][:zone] && !input[:properties][:zone].empty?
59
+ input[:request_params][:zone] = input[:properties][:zone]
60
+ end
61
+
62
+ Logger.info "Preprocess QingCloud request: [#{input[:id]}] #{input}"
63
+ input
64
+ end
65
+
66
+ def self.decorate_input(input)
67
+ input.deep_symbolize_keys!
68
+ input[:id] = (Random.new.rand * 1_000_000).to_int
69
+ compact input
70
+ end
71
+
72
+ def self.compact(object)
73
+ object.each do |k, v|
74
+ object[k] = compact v if v.is_a? Hash
75
+ object.delete k if v.nil? || v == ''
76
+ end
77
+ object
78
+ end
79
+ end
80
+ end
81
+ end
@@ -0,0 +1,80 @@
1
+ # +-------------------------------------------------------------------------
2
+ # | Copyright (C) 2016 Yunify, Inc.
3
+ # +-------------------------------------------------------------------------
4
+ # | Licensed under the Apache License, Version 2.0 (the "License");
5
+ # | you may not use this work except in compliance with the License.
6
+ # | You may obtain a copy of the License in the LICENSE file, or at:
7
+ # |
8
+ # | http://www.apache.org/licenses/LICENSE-2.0
9
+ # |
10
+ # | Unless required by applicable law or agreed to in writing, software
11
+ # | distributed under the License is distributed on an "AS IS" BASIS,
12
+ # | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # | See the License for the specific language governing permissions and
14
+ # | limitations under the License.
15
+ # +-------------------------------------------------------------------------
16
+
17
+ require 'json'
18
+ require 'net/http'
19
+ require 'ostruct'
20
+
21
+ module QingCloud
22
+ module SDK
23
+ class Request
24
+ attr_accessor :input, :request_url, :http_request, :http_response
25
+
26
+ def initialize(input)
27
+ self.input = Preprocessor.do input
28
+ end
29
+
30
+ def send
31
+ check
32
+ build
33
+ perform
34
+ unpack
35
+ end
36
+
37
+ private
38
+
39
+ def check
40
+ unless !input[:config][:qy_access_key_id].nil? && !input[:config][:qy_access_key_id].empty?
41
+ raise SDKError, 'access key not provided'
42
+ end
43
+ unless !input[:config][:qy_secret_access_key].nil? && !input[:config][:qy_secret_access_key].empty?
44
+ raise SDKError, 'secret access key not provided'
45
+ end
46
+ end
47
+
48
+ def build
49
+ self.input = Signer.do input
50
+
51
+ params = input[:request_params].map { |k, v| "#{k}=#{v}" }
52
+ query_string = !params.empty? ? "?#{params.join '&'}" : ''
53
+ self.request_url = "#{input[:request_endpoint]}#{input[:config][:uri]}#{query_string}"
54
+
55
+ self.http_request = Net::HTTP::Get.new request_url
56
+ end
57
+
58
+ def perform
59
+ retries = input[:config][:connection_retries]
60
+ while
61
+ begin
62
+ Logger.info "Sending request: [#{input[:id]}] #{request_url}"
63
+ self.http_response = input[:config].connection.request request_url, http_request
64
+ rescue SocketError
65
+ retries > 0 ? retries -= 1 : (raise NetworkError)
66
+ sleep 1
67
+ next
68
+ end
69
+ break
70
+ end
71
+ end
72
+
73
+ def unpack
74
+ output = JSON.parse(http_response.body)
75
+ Logger.info "Parse response: [#{input[:id]}] #{output}"
76
+ output.deep_symbolize_keys!
77
+ end
78
+ end
79
+ end
80
+ end