nucleus 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (224) hide show
  1. checksums.yaml +7 -0
  2. data/.gitattributes +1 -0
  3. data/.gitignore +19 -0
  4. data/.rspec +3 -0
  5. data/.rubocop.yml +44 -0
  6. data/.travis.yml +21 -0
  7. data/CHANGELOG.md +19 -0
  8. data/CONTRIBUTING.md +13 -0
  9. data/Gemfile +16 -0
  10. data/Guardfile +22 -0
  11. data/LICENSE +21 -0
  12. data/README.md +675 -0
  13. data/Rakefile +137 -0
  14. data/bin/nucleus +91 -0
  15. data/bin/nucleus.bat +1 -0
  16. data/config.ru +18 -0
  17. data/config/adapters/cloud_control.yml +32 -0
  18. data/config/adapters/cloud_foundry_v2.yml +61 -0
  19. data/config/adapters/heroku.yml +13 -0
  20. data/config/adapters/openshift_v2.yml +20 -0
  21. data/config/nucleus_config.rb +47 -0
  22. data/lib/nucleus.rb +13 -0
  23. data/lib/nucleus/adapter_resolver.rb +115 -0
  24. data/lib/nucleus/adapters/base_adapter.rb +109 -0
  25. data/lib/nucleus/adapters/buildpack_translator.rb +79 -0
  26. data/lib/nucleus/adapters/v1/cloud_control/application.rb +108 -0
  27. data/lib/nucleus/adapters/v1/cloud_control/authentication.rb +27 -0
  28. data/lib/nucleus/adapters/v1/cloud_control/buildpacks.rb +23 -0
  29. data/lib/nucleus/adapters/v1/cloud_control/cloud_control.rb +153 -0
  30. data/lib/nucleus/adapters/v1/cloud_control/data.rb +76 -0
  31. data/lib/nucleus/adapters/v1/cloud_control/domains.rb +68 -0
  32. data/lib/nucleus/adapters/v1/cloud_control/lifecycle.rb +27 -0
  33. data/lib/nucleus/adapters/v1/cloud_control/log_poller.rb +71 -0
  34. data/lib/nucleus/adapters/v1/cloud_control/logs.rb +103 -0
  35. data/lib/nucleus/adapters/v1/cloud_control/regions.rb +32 -0
  36. data/lib/nucleus/adapters/v1/cloud_control/scaling.rb +17 -0
  37. data/lib/nucleus/adapters/v1/cloud_control/semantic_errors.rb +31 -0
  38. data/lib/nucleus/adapters/v1/cloud_control/services.rb +162 -0
  39. data/lib/nucleus/adapters/v1/cloud_control/token.rb +17 -0
  40. data/lib/nucleus/adapters/v1/cloud_control/vars.rb +88 -0
  41. data/lib/nucleus/adapters/v1/cloud_foundry_v2/app_states.rb +28 -0
  42. data/lib/nucleus/adapters/v1/cloud_foundry_v2/application.rb +111 -0
  43. data/lib/nucleus/adapters/v1/cloud_foundry_v2/authentication.rb +17 -0
  44. data/lib/nucleus/adapters/v1/cloud_foundry_v2/buildpacks.rb +23 -0
  45. data/lib/nucleus/adapters/v1/cloud_foundry_v2/cloud_foundry_v2.rb +141 -0
  46. data/lib/nucleus/adapters/v1/cloud_foundry_v2/data.rb +97 -0
  47. data/lib/nucleus/adapters/v1/cloud_foundry_v2/domains.rb +149 -0
  48. data/lib/nucleus/adapters/v1/cloud_foundry_v2/lifecycle.rb +41 -0
  49. data/lib/nucleus/adapters/v1/cloud_foundry_v2/logs.rb +303 -0
  50. data/lib/nucleus/adapters/v1/cloud_foundry_v2/regions.rb +33 -0
  51. data/lib/nucleus/adapters/v1/cloud_foundry_v2/scaling.rb +15 -0
  52. data/lib/nucleus/adapters/v1/cloud_foundry_v2/semantic_errors.rb +27 -0
  53. data/lib/nucleus/adapters/v1/cloud_foundry_v2/services.rb +286 -0
  54. data/lib/nucleus/adapters/v1/cloud_foundry_v2/vars.rb +80 -0
  55. data/lib/nucleus/adapters/v1/heroku/app_states.rb +57 -0
  56. data/lib/nucleus/adapters/v1/heroku/application.rb +93 -0
  57. data/lib/nucleus/adapters/v1/heroku/authentication.rb +27 -0
  58. data/lib/nucleus/adapters/v1/heroku/buildpacks.rb +27 -0
  59. data/lib/nucleus/adapters/v1/heroku/data.rb +78 -0
  60. data/lib/nucleus/adapters/v1/heroku/domains.rb +43 -0
  61. data/lib/nucleus/adapters/v1/heroku/heroku.rb +146 -0
  62. data/lib/nucleus/adapters/v1/heroku/lifecycle.rb +51 -0
  63. data/lib/nucleus/adapters/v1/heroku/logs.rb +108 -0
  64. data/lib/nucleus/adapters/v1/heroku/regions.rb +42 -0
  65. data/lib/nucleus/adapters/v1/heroku/scaling.rb +28 -0
  66. data/lib/nucleus/adapters/v1/heroku/semantic_errors.rb +23 -0
  67. data/lib/nucleus/adapters/v1/heroku/services.rb +168 -0
  68. data/lib/nucleus/adapters/v1/heroku/vars.rb +65 -0
  69. data/lib/nucleus/adapters/v1/openshift_v2/app_states.rb +68 -0
  70. data/lib/nucleus/adapters/v1/openshift_v2/application.rb +108 -0
  71. data/lib/nucleus/adapters/v1/openshift_v2/authentication.rb +21 -0
  72. data/lib/nucleus/adapters/v1/openshift_v2/data.rb +96 -0
  73. data/lib/nucleus/adapters/v1/openshift_v2/domains.rb +37 -0
  74. data/lib/nucleus/adapters/v1/openshift_v2/lifecycle.rb +60 -0
  75. data/lib/nucleus/adapters/v1/openshift_v2/logs.rb +106 -0
  76. data/lib/nucleus/adapters/v1/openshift_v2/openshift_v2.rb +125 -0
  77. data/lib/nucleus/adapters/v1/openshift_v2/regions.rb +58 -0
  78. data/lib/nucleus/adapters/v1/openshift_v2/scaling.rb +39 -0
  79. data/lib/nucleus/adapters/v1/openshift_v2/semantic_errors.rb +40 -0
  80. data/lib/nucleus/adapters/v1/openshift_v2/services.rb +173 -0
  81. data/lib/nucleus/adapters/v1/openshift_v2/vars.rb +49 -0
  82. data/lib/nucleus/adapters/v1/stub_adapter.rb +464 -0
  83. data/lib/nucleus/core/adapter_authentication_inductor.rb +62 -0
  84. data/lib/nucleus/core/adapter_extensions/auth/auth_client.rb +44 -0
  85. data/lib/nucleus/core/adapter_extensions/auth/authentication_retry_wrapper.rb +79 -0
  86. data/lib/nucleus/core/adapter_extensions/auth/expiring_token_auth_client.rb +53 -0
  87. data/lib/nucleus/core/adapter_extensions/auth/http_basic_auth_client.rb +37 -0
  88. data/lib/nucleus/core/adapter_extensions/auth/o_auth2_auth_client.rb +95 -0
  89. data/lib/nucleus/core/adapter_extensions/auth/token_auth_client.rb +36 -0
  90. data/lib/nucleus/core/adapter_extensions/http_client.rb +177 -0
  91. data/lib/nucleus/core/adapter_extensions/http_tail_client.rb +26 -0
  92. data/lib/nucleus/core/adapter_extensions/tail_stopper.rb +25 -0
  93. data/lib/nucleus/core/common/errors/ambiguous_adapter_error.rb +7 -0
  94. data/lib/nucleus/core/common/errors/file_existence_error.rb +7 -0
  95. data/lib/nucleus/core/common/errors/startup_error.rb +12 -0
  96. data/lib/nucleus/core/common/exit_codes.rb +25 -0
  97. data/lib/nucleus/core/common/files/application_repo_sanitizer.rb +52 -0
  98. data/lib/nucleus/core/common/files/archive_extractor.rb +112 -0
  99. data/lib/nucleus/core/common/files/archiver.rb +91 -0
  100. data/lib/nucleus/core/common/link_generator.rb +46 -0
  101. data/lib/nucleus/core/common/logging/logging.rb +52 -0
  102. data/lib/nucleus/core/common/logging/multi_logger.rb +59 -0
  103. data/lib/nucleus/core/common/logging/request_log_formatter.rb +48 -0
  104. data/lib/nucleus/core/common/ssh_handler.rb +108 -0
  105. data/lib/nucleus/core/common/stream_callback.rb +27 -0
  106. data/lib/nucleus/core/common/thread_config_accessor.rb +85 -0
  107. data/lib/nucleus/core/common/url_converter.rb +28 -0
  108. data/lib/nucleus/core/enums/application_states.rb +26 -0
  109. data/lib/nucleus/core/enums/logfile_types.rb +28 -0
  110. data/lib/nucleus/core/error_messages.rb +127 -0
  111. data/lib/nucleus/core/errors/adapter_error.rb +13 -0
  112. data/lib/nucleus/core/errors/adapter_missing_implementation_error.rb +12 -0
  113. data/lib/nucleus/core/errors/adapter_request_error.rb +10 -0
  114. data/lib/nucleus/core/errors/adapter_resource_not_found_error.rb +10 -0
  115. data/lib/nucleus/core/errors/endpoint_authentication_error.rb +10 -0
  116. data/lib/nucleus/core/errors/platform_specific_semantic_error.rb +12 -0
  117. data/lib/nucleus/core/errors/platform_timeout_error.rb +10 -0
  118. data/lib/nucleus/core/errors/platform_unavailable_error.rb +10 -0
  119. data/lib/nucleus/core/errors/semantic_adapter_request_error.rb +19 -0
  120. data/lib/nucleus/core/errors/unknown_adapter_call_error.rb +10 -0
  121. data/lib/nucleus/core/file_handling/archive_converter.rb +29 -0
  122. data/lib/nucleus/core/file_handling/file_manager.rb +64 -0
  123. data/lib/nucleus/core/file_handling/git_deployer.rb +133 -0
  124. data/lib/nucleus/core/file_handling/git_repo_analyzer.rb +23 -0
  125. data/lib/nucleus/core/import/adapter_configuration.rb +53 -0
  126. data/lib/nucleus/core/import/vendor_parser.rb +28 -0
  127. data/lib/nucleus/core/import/version_detector.rb +18 -0
  128. data/lib/nucleus/core/models/abstract_model.rb +29 -0
  129. data/lib/nucleus/core/models/endpoint.rb +30 -0
  130. data/lib/nucleus/core/models/provider.rb +26 -0
  131. data/lib/nucleus/core/models/vendor.rb +22 -0
  132. data/lib/nucleus/ext/kernel.rb +5 -0
  133. data/lib/nucleus/ext/regexp.rb +49 -0
  134. data/lib/nucleus/os.rb +15 -0
  135. data/lib/nucleus/root_dir.rb +13 -0
  136. data/lib/nucleus/scripts/finalize.rb +8 -0
  137. data/lib/nucleus/scripts/initialize.rb +9 -0
  138. data/lib/nucleus/scripts/initialize_config_defaults.rb +26 -0
  139. data/lib/nucleus/scripts/load.rb +17 -0
  140. data/lib/nucleus/scripts/load_dependencies.rb +43 -0
  141. data/lib/nucleus/scripts/setup_config.rb +28 -0
  142. data/lib/nucleus/scripts/shutdown.rb +11 -0
  143. data/lib/nucleus/version.rb +3 -0
  144. data/nucleus.gemspec +88 -0
  145. data/public/robots.txt +2 -0
  146. data/public/swagger-ui/css/reset.css +125 -0
  147. data/public/swagger-ui/css/screen.css +1224 -0
  148. data/public/swagger-ui/images/apple-touch-icon-114x114.png +0 -0
  149. data/public/swagger-ui/images/apple-touch-icon-120x120.png +0 -0
  150. data/public/swagger-ui/images/apple-touch-icon-144x144.png +0 -0
  151. data/public/swagger-ui/images/apple-touch-icon-152x152.png +0 -0
  152. data/public/swagger-ui/images/apple-touch-icon-57x57.png +0 -0
  153. data/public/swagger-ui/images/apple-touch-icon-60x60.png +0 -0
  154. data/public/swagger-ui/images/apple-touch-icon-72x72.png +0 -0
  155. data/public/swagger-ui/images/apple-touch-icon-76x76.png +0 -0
  156. data/public/swagger-ui/images/explorer_icons.png +0 -0
  157. data/public/swagger-ui/images/favicon-128.png +0 -0
  158. data/public/swagger-ui/images/favicon-16x16.png +0 -0
  159. data/public/swagger-ui/images/favicon-196x196.png +0 -0
  160. data/public/swagger-ui/images/favicon-32x32.png +0 -0
  161. data/public/swagger-ui/images/favicon-96x96.png +0 -0
  162. data/public/swagger-ui/images/favicon.ico +0 -0
  163. data/public/swagger-ui/images/logo_small.png +0 -0
  164. data/public/swagger-ui/images/mstile-144x144.png +0 -0
  165. data/public/swagger-ui/images/mstile-150x150.png +0 -0
  166. data/public/swagger-ui/images/mstile-310x150.png +0 -0
  167. data/public/swagger-ui/images/mstile-310x310.png +0 -0
  168. data/public/swagger-ui/images/mstile-70x70.png +0 -0
  169. data/public/swagger-ui/images/pet_store_api.png +0 -0
  170. data/public/swagger-ui/images/throbber.gif +0 -0
  171. data/public/swagger-ui/images/wordnik_api.png +0 -0
  172. data/public/swagger-ui/index.html +107 -0
  173. data/public/swagger-ui/lib/backbone-min.js +38 -0
  174. data/public/swagger-ui/lib/handlebars-1.0.0.js +2278 -0
  175. data/public/swagger-ui/lib/highlight.7.3.pack.js +1 -0
  176. data/public/swagger-ui/lib/jquery-1.8.0.min.js +2 -0
  177. data/public/swagger-ui/lib/jquery.ba-bbq.min.js +18 -0
  178. data/public/swagger-ui/lib/jquery.slideto.min.js +1 -0
  179. data/public/swagger-ui/lib/jquery.wiggle.min.js +8 -0
  180. data/public/swagger-ui/lib/shred.bundle.js +2765 -0
  181. data/public/swagger-ui/lib/shred/content.js +193 -0
  182. data/public/swagger-ui/lib/swagger-oauth.js +211 -0
  183. data/public/swagger-ui/lib/swagger.js +1653 -0
  184. data/public/swagger-ui/lib/underscore-min.js +32 -0
  185. data/public/swagger-ui/o2c.html +15 -0
  186. data/public/swagger-ui/redirect.html +14 -0
  187. data/public/swagger-ui/swagger-ui.js +2324 -0
  188. data/public/swagger-ui/swagger-ui.min.js +1 -0
  189. data/schemas/api.adapter.schema.yml +31 -0
  190. data/schemas/api.requirements.schema.yml +17 -0
  191. data/spec/factories/models.rb +61 -0
  192. data/spec/integration/api/auth_spec.rb +58 -0
  193. data/spec/integration/api/endpoints_spec.rb +167 -0
  194. data/spec/integration/api/errors_spec.rb +47 -0
  195. data/spec/integration/api/providers_spec.rb +157 -0
  196. data/spec/integration/api/swagger_schema_spec.rb +64 -0
  197. data/spec/integration/api/vendors_spec.rb +45 -0
  198. data/spec/integration/integration_spec_helper.rb +27 -0
  199. data/spec/integration/test_data_generator.rb +55 -0
  200. data/spec/nucleus_git_key.pem +51 -0
  201. data/spec/spec_helper.rb +98 -0
  202. data/spec/support/shared_example_request_types.rb +99 -0
  203. data/spec/test_suites.rake +31 -0
  204. data/spec/unit/adapters/archive_converter_spec.rb +25 -0
  205. data/spec/unit/adapters/file_manager_spec.rb +93 -0
  206. data/spec/unit/adapters/git_deployer_spec.rb +262 -0
  207. data/spec/unit/adapters/v1/stub_spec.rb +14 -0
  208. data/spec/unit/common/helpers/auth_helper_spec.rb +73 -0
  209. data/spec/unit/common/oauth2_auth_client_spec.rb +108 -0
  210. data/spec/unit/common/regexp_spec.rb +33 -0
  211. data/spec/unit/common/request_log_formatter_spec.rb +108 -0
  212. data/spec/unit/common/thread_config_accessor_spec.rb +97 -0
  213. data/spec/unit/models/endpoint_spec.rb +83 -0
  214. data/spec/unit/models/provider_spec.rb +102 -0
  215. data/spec/unit/models/vendor_spec.rb +100 -0
  216. data/spec/unit/schemas/adapter_schema_spec.rb +16 -0
  217. data/spec/unit/schemas/adapter_validation_spec.rb +56 -0
  218. data/spec/unit/schemas/requirements_schema_spec.rb +16 -0
  219. data/spec/unit/unit_spec_helper.rb +11 -0
  220. data/tasks/compatibility.rake +113 -0
  221. data/tasks/evaluation.rake +162 -0
  222. data/wiki/adapter_tests.md +99 -0
  223. data/wiki/implement_new_adapter.md +155 -0
  224. metadata +836 -0
@@ -0,0 +1,108 @@
1
+ require 'spec/unit/unit_spec_helper'
2
+
3
+ describe Nucleus::Adapters::OAuth2AuthClient do
4
+ describe 'initialization' do
5
+ it 'applies all values correctly' do
6
+ url = 'theurl'
7
+ check_certs = false
8
+ client = Nucleus::Adapters::OAuth2AuthClient.new url, check_certs
9
+ expect(client.instance_variable_get :@auth_url).to be url
10
+ expect(client.verify_ssl).to be check_certs
11
+ end
12
+ end
13
+
14
+ describe 'functionality:' do
15
+ subject(:client) { Nucleus::Adapters::OAuth2AuthClient.new 'http://localhost', true }
16
+ let!(:invalid_username) { 'invalid_username' }
17
+ let!(:invalid_password) { 'invalid_password' }
18
+ let!(:valid_username) { 'valid_username' }
19
+ let!(:valid_password) { 'valid_password' }
20
+ let!(:valid_refresh_token) { 'valid_refresh_token' }
21
+ let!(:invalid_refresh_token) { 'invalid_refresh_token' }
22
+
23
+ before do
24
+ Excon.stub({ query: { grant_type: 'password', username: valid_username, password: valid_password } },
25
+ body: { access_token: 'access_token', refresh_token: valid_refresh_token,
26
+ expires_in: 3600, token_type: 'bearer' }.to_json, status: 200)
27
+ Excon.stub({ query: { grant_type: 'password', username: invalid_username, password: invalid_password } },
28
+ body: { error: 'code', error_description: 'description' }.to_json, status: 401)
29
+ Excon.stub({ query: { grant_type: 'refresh_token', refresh_token: valid_refresh_token } },
30
+ body: { access_token: 'refreshed_access_token', expires_in: 3600,
31
+ token_type: 'bearer' }.to_json, status: 200)
32
+ Excon.stub({ query: { grant_type: 'refresh_token', refresh_token: invalid_refresh_token } },
33
+ body: { error: 'code', error_description: 'description' }.to_json, status: 401)
34
+ end
35
+
36
+ context 'when not authenticated' do
37
+ describe '#authenticate' do
38
+ context 'with invalid credentials' do
39
+ it 'raises an error when authentication failed' do
40
+ expect { client.authenticate(invalid_username, invalid_password) }.to raise_error(
41
+ Nucleus::Errors::EndpointAuthenticationError)
42
+ end
43
+ end
44
+
45
+ context 'with valid credentials' do
46
+ it 'returns the self instance' do
47
+ expect(client.authenticate(valid_username, valid_password))
48
+ .to be_a Nucleus::Adapters::OAuth2AuthClient
49
+ end
50
+ end
51
+ end
52
+ describe '#refresh' do
53
+ it 'can not be invoked' do
54
+ expect { client.refresh }.to raise_error(Nucleus::Errors::EndpointAuthenticationError)
55
+ end
56
+ end
57
+ describe '#auth_header' do
58
+ it 'can not be invoked' do
59
+ expect { client.auth_header }.to raise_error(Nucleus::Errors::EndpointAuthenticationError)
60
+ end
61
+ end
62
+ end
63
+
64
+ context 'when authenticated' do
65
+ before { client.authenticate(valid_username, valid_password) }
66
+ describe '#authenticate' do
67
+ context 'with invalid credentials' do
68
+ before { Excon.stub({}, body: {}, status: 400) }
69
+ it 'returns instance without making new auth request' do
70
+ expect(client.authenticate(valid_username, valid_password)).to be_a Nucleus::Adapters::OAuth2AuthClient
71
+ end
72
+ end
73
+ context 'with valid credentials' do
74
+ it 'returns instance without making new auth request' do
75
+ expect(client.authenticate(valid_username, valid_password)).to be_a Nucleus::Adapters::OAuth2AuthClient
76
+ end
77
+ end
78
+ end
79
+ describe '#auth_header' do
80
+ context 'when not expired' do
81
+ it 'returns an authorization header' do
82
+ expect(client.auth_header).to have_key('Authorization')
83
+ expect(client.auth_header['Authorization']).to eq 'bearer access_token'
84
+ end
85
+ end
86
+ context 'when expired' do
87
+ before do
88
+ client.instance_variable_set :@expiration, (Time.now - 120)
89
+ end
90
+ it 'returns an updated authorization header' do
91
+ expect(client.auth_header).to have_key('Authorization')
92
+ expect(client.auth_header['Authorization']).to eq 'bearer refreshed_access_token'
93
+ end
94
+ end
95
+ end
96
+ describe '#refresh' do
97
+ before { client.refresh }
98
+ it 'returns the self instance' do
99
+ expect(client.refresh).to be_a Nucleus::Adapters::OAuth2AuthClient
100
+ end
101
+ it 'makes an updated authorization header available' do
102
+ expect(client.auth_header).to have_key('Authorization')
103
+ expect(client.auth_header['Authorization']).to eq 'bearer refreshed_access_token'
104
+ end
105
+ end
106
+ end
107
+ end
108
+ end
@@ -0,0 +1,33 @@
1
+ # encoding: utf-8
2
+ require 'spec/unit/unit_spec_helper'
3
+ require 'nucleus/ext/regexp'
4
+
5
+ describe 'Regexp::PERFECT_URL_PATTERN' do
6
+ %w(
7
+ http://✪df.ws/123 http://userid:password@example.com:8080 http://userid:password@example.com:8080/
8
+ http://userid@example.com http://userid@example.com/ http://userid@example.com:8080 http://userid@example.com:8080/
9
+ http://userid:password@example.com http://userid:password@example.com/ http://142.42.1.1/ http://142.42.1.1:8080/
10
+ http://➡.ws/䨹 http://⌘.ws http://⌘.ws/ http://foo.com/blah_(wikipedia)#cite-1
11
+ http://foo.com/blah_(wikipedia)_blah#cite-1 http://foo.com/unicode_(✪)_in_parens
12
+ http://foo.com/(something)?after=parens http://☺.damowmow.com/ http://code.google.com/events/#&product=browser
13
+ http://j.mp ftp://foo.bar/baz http://foo.bar/?q=Test%20URL-encoded%20stuff http://مثال.إختبار
14
+ http://例子.测试).each do |valid_url|
15
+ it "matches #{valid_url}" do
16
+ expect(Regexp::PERFECT_URL_PATTERN =~ valid_url).to eq 0
17
+ end
18
+ end
19
+
20
+ [
21
+ 'http://', 'http://.', 'http://..', 'http://../', 'http://?', 'http://??', 'http://??/', 'http://#', 'http://##',
22
+ 'http://##/', 'http://foo.bar?q=Spaces should be encoded', '//', '//a', '///a', '///', 'http:///a', 'foo.com',
23
+ 'rdar://1234', 'h://test', 'http:// shouldfail.com', ':// should fail', 'http://foo.bar/foo(bar)baz quux',
24
+ 'ftps://foo.bar/', 'http://-error-.invalid/', 'http://a.b--c.de/', 'http://-a.b.co', 'http://a.b-.co',
25
+ 'http://0.0.0.0', 'http://10.1.1.0', 'http://10.1.1.255', 'http://224.1.1.1', 'http://1.1.1.1.1',
26
+ 'http://123.123.123', 'http://3628126748', 'http://.www.foo.bar/', 'http://www.foo.bar./', 'http://.www.foo.bar./',
27
+ 'http://10.1.1.1', 'http://10.1.1.254'
28
+ ].each do |invalid_url|
29
+ it "does not match #{invalid_url}" do
30
+ expect(Regexp::PERFECT_URL_PATTERN =~ invalid_url).to be_nil
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,108 @@
1
+ describe Nucleus::Logging::Formatter do
2
+ subject { Nucleus::Logging::Formatter.new }
3
+ let(:request_id) { SecureRandom.uuid }
4
+ let(:severity) { Logger::Severity::WARN.to_s }
5
+ let(:time) { Time.now }
6
+ let(:prog) { 'progname' }
7
+ let(:msg) { 'This output shall be included in the log' }
8
+
9
+ # make sure nucleus_request_id is always reset
10
+ before(:each) { Thread.current[:nucleus_request_id] = nil }
11
+
12
+ context 'with nucleus_request_id assigned to the current thread' do
13
+ before do
14
+ Thread.current[:nucleus_request_id] = request_id
15
+ @response = subject.call(severity, time, prog, msg)
16
+ end
17
+
18
+ it 'does include the request_id' do
19
+ expect(@response).to include(request_id)
20
+ end
21
+ it 'includes the program name' do
22
+ expect(@response).to include(prog)
23
+ end
24
+ it 'includes the actual log message' do
25
+ expect(@response).to include(msg)
26
+ end
27
+ it 'ends with a newline' do
28
+ expect(@response).to end_with("\n")
29
+ end
30
+ end
31
+
32
+ context 'nucleus_request_id unassigned' do
33
+ let(:dateformat) { '%Y-%m-%d' }
34
+ before do
35
+ subject.datetime_format = dateformat
36
+ @response = subject.call(severity, time, prog, msg)
37
+ end
38
+
39
+ it 'does not include the request_id' do
40
+ expect(@response).to_not include(request_id)
41
+ end
42
+ it 'includes the program name' do
43
+ expect(@response).to include(prog)
44
+ end
45
+ it 'includes the actual log message' do
46
+ expect(@response).to include(msg)
47
+ end
48
+ it 'ends with a newline' do
49
+ expect(@response).to end_with("\n")
50
+ end
51
+ it 'does included the time formatted according to the specified format' do
52
+ expect(@response).to include(time.strftime(dateformat))
53
+ end
54
+ end
55
+
56
+ context 'nucleus_request_id unassigned' do
57
+ before { @response = subject.call(severity, time, prog, msg) }
58
+
59
+ it 'does not include the request_id' do
60
+ expect(@response).to_not include(request_id)
61
+ end
62
+ it 'includes the program name' do
63
+ expect(@response).to include(prog)
64
+ end
65
+ it 'includes the actual log message' do
66
+ expect(@response).to include(msg)
67
+ end
68
+ it 'ends with a newline' do
69
+ expect(@response).to end_with("\n")
70
+ end
71
+ end
72
+
73
+ context 'with an exception as error message' do
74
+ let(:error) { StandardError.new(msg) }
75
+ before { @response = subject.call(severity, time, prog, error) }
76
+
77
+ it 'does not include the request_id' do
78
+ expect(@response).to_not include(request_id)
79
+ end
80
+ it 'includes the program name' do
81
+ expect(@response).to include(prog)
82
+ end
83
+ it 'includes the actual log message' do
84
+ expect(@response).to include(msg)
85
+ end
86
+ it 'ends with a newline' do
87
+ expect(@response).to end_with("\n")
88
+ end
89
+ end
90
+
91
+ context 'with an object as error message' do
92
+ let(:object) { { hashkey: 'hashvalue' } }
93
+ before { @response = subject.call(severity, time, prog, object) }
94
+
95
+ it 'does not include the request_id' do
96
+ expect(@response).to_not include(request_id)
97
+ end
98
+ it 'includes the program name' do
99
+ expect(@response).to include(prog)
100
+ end
101
+ it 'includes the actual log message' do
102
+ expect(@response).to include(object.inspect)
103
+ end
104
+ it 'ends with a newline' do
105
+ expect(@response).to end_with("\n")
106
+ end
107
+ end
108
+ end
@@ -0,0 +1,97 @@
1
+ require 'spec/unit/unit_spec_helper'
2
+ require 'nucleus/core/common/thread_config_accessor'
3
+
4
+ class ThreadedConfig
5
+ thread_config_accessor :setting_a, default: 5
6
+ end
7
+
8
+ class ThreadedConfigParentA
9
+ end
10
+
11
+ class ThreadedConfigParentB
12
+ thread_config_accessor :setting_a, default: 13
13
+ end
14
+
15
+ class ThreadedConfigChildA < ThreadedConfigParentA
16
+ thread_config_accessor :setting_a, default: 11
17
+ end
18
+
19
+ class ThreadedConfigChildB < ThreadedConfigParentB
20
+ end
21
+
22
+ class ThreadedConfigReadOnly
23
+ thread_config_accessor_readonly :setting_a, default: 7
24
+ end
25
+
26
+ describe 'ThreadConfigAccessor' do
27
+ describe 'config values accessibility' do
28
+ it 'for config defined in base class shall be available to inheriting classes' do
29
+ child = ThreadedConfigChildB.new
30
+ expect(child.setting_a).to eql 13
31
+ child.setting_a = 17
32
+ expect(child.setting_a).to eql 17
33
+ expect(child.setting_a).to eql ThreadedConfigParentB.setting_a
34
+ ThreadedConfigParentB.setting_a = 19
35
+ expect(child.setting_a).to eql ThreadedConfigParentB.setting_a
36
+ expect(child.setting_a).to eql 19
37
+ end
38
+
39
+ it 'for config defined in inheriting class shall not be available to parent classes' do
40
+ child = ThreadedConfigChildA.new
41
+ expect(child.setting_a).to eql 11
42
+ expect { ThreadedConfigParentA.setting_a }.to raise_error(NoMethodError)
43
+ end
44
+ end
45
+
46
+ describe 'using #thread_config_accessor' do
47
+ before :all do
48
+ # create instance
49
+ @config = ThreadedConfig.new
50
+ # assign value to the class
51
+ ThreadedConfig.setting_a = 1
52
+ end
53
+
54
+ it 'should have the same value on the class and instance' do
55
+ expect(@config.setting_a).to eql 1
56
+ expect(@config.setting_a).to eql ThreadedConfig.setting_a
57
+ end
58
+
59
+ it 'should have the different values in a new thread' do
60
+ Thread.new do
61
+ @config.setting_a = 2
62
+ expect(@config.setting_a).to eql 2
63
+ expect(@config.setting_a).to eql ThreadedConfig.setting_a
64
+ end.join
65
+ end
66
+
67
+ it 'should have the default values in a new thread' do
68
+ Thread.new do
69
+ expect(@config.setting_a).to eql 5
70
+ expect(@config.setting_a).to eql ThreadedConfig.setting_a
71
+ end.join
72
+ end
73
+ end
74
+
75
+ describe 'using #thread_config_accessor_readonly' do
76
+ before :all do
77
+ # create instance
78
+ @config = ThreadedConfigReadOnly.new
79
+ end
80
+
81
+ it 'should have the same value on the class and instance' do
82
+ expect(@config.setting_a).to eql 7
83
+ expect(@config.setting_a).to eql ThreadedConfigReadOnly.setting_a
84
+ end
85
+
86
+ it 'should keep the same default values in a new thread' do
87
+ Thread.new do
88
+ expect(@config.setting_a).to eql 7
89
+ expect(@config.setting_a).to eql ThreadedConfigReadOnly.setting_a
90
+ end.join
91
+ end
92
+
93
+ it 'should not allow to change the default values' do
94
+ Thread.new { expect { @config.setting_a = 10 }.to raise_error(NoMethodError) }.join
95
+ end
96
+ end
97
+ end
@@ -0,0 +1,83 @@
1
+ require 'spec/unit/unit_spec_helper'
2
+
3
+ describe Nucleus::Endpoint do
4
+ let(:id) { 'a123av6172812' }
5
+ let(:name) { 'fake endpoint name' }
6
+ let(:created_at) { Time.now }
7
+ let(:updated_at) { Time.now.to_s }
8
+ let(:url) { 'api.example.org' }
9
+ let(:app_domain) { 'apps.example.org' }
10
+ let(:trust) { true }
11
+
12
+ describe 'can be initialized with' do
13
+ context 'an empty hash and' do
14
+ before do
15
+ @endpoint = Nucleus::Endpoint.new({})
16
+ end
17
+ it 'fields are empty' do
18
+ expect(@endpoint.id).to be_nil
19
+ expect(@endpoint.name).to be_nil
20
+ expect(@endpoint.created_at).to be_nil
21
+ expect(@endpoint.updated_at).to be_nil
22
+ expect(@endpoint.url).to be_nil
23
+ expect(@endpoint.app_domain).to be_nil
24
+ end
25
+ it 'trust is set to false by default' do
26
+ expect(@endpoint.trust).to eql(false)
27
+ end
28
+ it 'to_s does not crash' do
29
+ expect { @endpoint.to_s }.to_not raise_error
30
+ end
31
+ end
32
+
33
+ context 'nil and' do
34
+ before do
35
+ @endpoint = Nucleus::Endpoint.new
36
+ end
37
+ it 'fields are empty' do
38
+ expect(@endpoint.id).to be_nil
39
+ expect(@endpoint.name).to be_nil
40
+ expect(@endpoint.created_at).to be_nil
41
+ expect(@endpoint.updated_at).to be_nil
42
+ expect(@endpoint.url).to be_nil
43
+ expect(@endpoint.app_domain).to be_nil
44
+ end
45
+ it 'trust is set to false by default' do
46
+ expect(@endpoint.trust).to eql(false)
47
+ end
48
+ it 'to_s does not crash' do
49
+ expect { @endpoint.to_s }.to_not raise_error
50
+ end
51
+ end
52
+
53
+ context 'hash properties' do
54
+ before do
55
+ @endpoint = Nucleus::Endpoint.new('id' => id, 'name' => name, 'created_at' => created_at,
56
+ 'updated_at' => updated_at, 'trust' => trust, 'app_domain' => app_domain,
57
+ 'url' => url)
58
+ end
59
+ it 'fields are not nil' do
60
+ expect(@endpoint.id).to_not be_nil
61
+ expect(@endpoint.name).to_not be_nil
62
+ expect(@endpoint.url).to_not be_nil
63
+ expect(@endpoint.app_domain).to_not be_nil
64
+ expect(@endpoint.trust).to_not be_nil
65
+ end
66
+ it 'dates and parent provider wont be applied' do
67
+ expect(@endpoint.created_at).to be_nil
68
+ expect(@endpoint.updated_at).to be_nil
69
+ expect(@endpoint.provider).to be_nil
70
+ end
71
+ it 'fields have the valid values assigned' do
72
+ expect(@endpoint.id).to eql(id)
73
+ expect(@endpoint.name).to eql(name)
74
+ expect(@endpoint.url).to eql(url)
75
+ expect(@endpoint.app_domain).to eql(app_domain)
76
+ expect(@endpoint.trust).to eql(trust)
77
+ end
78
+ it 'to_s does not crash' do
79
+ expect { @endpoint.to_s }.to_not raise_error
80
+ end
81
+ end
82
+ end
83
+ end
@@ -0,0 +1,102 @@
1
+ require 'spec/unit/unit_spec_helper'
2
+
3
+ describe Nucleus::Provider do
4
+ let(:id) { '67890' }
5
+ let(:name) { 'fake provider name' }
6
+ let(:created_at) { Time.now }
7
+ let(:updated_at) { Time.now.to_s }
8
+
9
+ describe 'can be initialized with' do
10
+ context 'an empty hash and' do
11
+ before do
12
+ @provider = Nucleus::Provider.new({})
13
+ end
14
+ it 'endpoints are empty' do
15
+ expect(@provider.endpoints).to eql([])
16
+ end
17
+ it 'fields are empty' do
18
+ expect(@provider.id).to be_nil
19
+ expect(@provider.name).to be_nil
20
+ expect(@provider.created_at).to be_nil
21
+ expect(@provider.updated_at).to be_nil
22
+ end
23
+ it 'to_s does not crash' do
24
+ expect { @provider.to_s }.to_not raise_error
25
+ end
26
+ end
27
+
28
+ context 'nil and' do
29
+ before do
30
+ @provider = Nucleus::Provider.new
31
+ end
32
+ it 'providers are empty' do
33
+ expect(@provider.endpoints).to eql([])
34
+ end
35
+ it 'fields are empty' do
36
+ expect(@provider.id).to be_nil
37
+ expect(@provider.name).to be_nil
38
+ expect(@provider.created_at).to be_nil
39
+ expect(@provider.updated_at).to be_nil
40
+ end
41
+ it 'to_s does not crash' do
42
+ expect { @provider.to_s }.to_not raise_error
43
+ end
44
+ end
45
+
46
+ context 'hash properties and endpoint double' do
47
+ before do
48
+ endpoint = instance_double('Nucleus::Endpoint', name: 'endpoint name')
49
+ allow(endpoint).to receive(:is_a?).with(Nucleus::Endpoint).and_return(true)
50
+ @provider = Nucleus::Provider.new('endpoints' => [endpoint], 'id' => id, 'name' => name,
51
+ 'created_at' => created_at, 'updated_at' => updated_at)
52
+ end
53
+ it 'has one endpoint' do
54
+ expect(@provider.endpoints).to_not eql([])
55
+ expect(@provider.endpoints.length).to eql(1)
56
+ end
57
+ it 'fields are not nil' do
58
+ expect(@provider.id).to_not be_nil
59
+ expect(@provider.name).to_not be_nil
60
+ end
61
+ it 'dates and parent vendor wont be applied' do
62
+ expect(@provider.created_at).to be_nil
63
+ expect(@provider.updated_at).to be_nil
64
+ expect(@provider.vendor).to be_nil
65
+ end
66
+ it 'fields have the valid values assigned' do
67
+ expect(@provider.id).to eql(id)
68
+ expect(@provider.name).to eql(name)
69
+ end
70
+ it 'to_s does not crash' do
71
+ expect { @provider.to_s }.to_not raise_error
72
+ end
73
+ end
74
+
75
+ context 'hash properties and endpoint hash' do
76
+ before do
77
+ @provider = Nucleus::Provider.new('endpoints' => [{ 'name' => 'endpoint name' }], 'id' => id, 'name' => name,
78
+ 'created_at' => created_at, 'updated_at' => updated_at)
79
+ end
80
+ it 'has one endpoint' do
81
+ expect(@provider.endpoints).to_not eql([])
82
+ expect(@provider.endpoints.length).to eql(1)
83
+ end
84
+ it 'fields are not nil' do
85
+ expect(@provider.id).to_not be_nil
86
+ expect(@provider.name).to_not be_nil
87
+ end
88
+ it 'dates and parent vendor wont be applied' do
89
+ expect(@provider.created_at).to be_nil
90
+ expect(@provider.updated_at).to be_nil
91
+ expect(@provider.vendor).to be_nil
92
+ end
93
+ it 'fields have the valid values assigned' do
94
+ expect(@provider.id).to eql(id)
95
+ expect(@provider.name).to eql(name)
96
+ end
97
+ it 'to_s does not crash' do
98
+ expect { @provider.to_s }.to_not raise_error
99
+ end
100
+ end
101
+ end
102
+ end