deltacloud-core 0.5.0 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- data/NOTICE +1 -1
- data/Rakefile +63 -21
- data/bin/deltacloudd +10 -6
- data/config.ru +62 -6
- data/config/drivers/ec2.yaml +8 -0
- data/config/drivers/fgcp.yaml +13 -0
- data/deltacloud-core.gemspec +10 -2
- data/lib/cimi/collections.rb +58 -0
- data/lib/cimi/collections/address_templates.rb +49 -0
- data/lib/cimi/collections/addresses.rb +74 -0
- data/lib/cimi/collections/cloud_entry_point.rb +37 -0
- data/lib/{deltacloud/helpers/conversion_helper.rb → cimi/collections/entity_metadata.rb} +24 -16
- data/lib/cimi/collections/machine_admins.rb +74 -0
- data/lib/cimi/collections/machine_configurations.rb +49 -0
- data/lib/cimi/collections/machine_images.rb +50 -0
- data/lib/cimi/collections/machines.rb +157 -0
- data/lib/cimi/collections/network_configurations.rb +47 -0
- data/lib/cimi/collections/network_templates.rb +48 -0
- data/lib/cimi/collections/networks.rb +125 -0
- data/lib/cimi/collections/routing_group_templates.rb +47 -0
- data/lib/cimi/collections/routing_groups.rb +48 -0
- data/lib/cimi/collections/volume_configurations.rb +48 -0
- data/lib/cimi/collections/volume_images.rb +50 -0
- data/lib/cimi/collections/volumes.rb +80 -0
- data/lib/cimi/collections/vsp_configurations.rb +48 -0
- data/lib/cimi/collections/vsp_templates.rb +50 -0
- data/lib/cimi/collections/vsps.rb +108 -0
- data/lib/cimi/dependencies.rb +1 -0
- data/lib/cimi/helpers.rb +116 -0
- data/lib/cimi/helpers/cimi_helper.rb +6 -2
- data/lib/cimi/models.rb +72 -0
- data/lib/cimi/{model → models}/action.rb +1 -1
- data/lib/cimi/models/address.rb +72 -0
- data/lib/cimi/models/address_collection.rb +34 -0
- data/lib/cimi/models/address_template.rb +54 -0
- data/lib/cimi/models/address_template_collection.rb +34 -0
- data/lib/cimi/{model → models}/base.rb +2 -2
- data/lib/cimi/{model → models}/cloud_entry_point.rb +3 -5
- data/lib/cimi/{model → models}/entity_metadata.rb +7 -6
- data/lib/cimi/{model → models}/entity_metadata_collection.rb +2 -2
- data/lib/cimi/{model → models}/errors.rb +8 -0
- data/lib/cimi/{model → models}/machine.rb +10 -10
- data/lib/cimi/{model → models}/machine_admin.rb +1 -1
- data/lib/cimi/{model → models}/machine_admin_collection.rb +2 -2
- data/lib/cimi/{model → models}/machine_collection.rb +2 -2
- data/lib/cimi/{model → models}/machine_configuration.rb +9 -6
- data/lib/cimi/{model → models}/machine_configuration_collection.rb +2 -2
- data/lib/cimi/{model → models}/machine_image.rb +1 -1
- data/lib/cimi/{model → models}/machine_image_collection.rb +2 -2
- data/lib/cimi/{model → models}/machine_template.rb +0 -0
- data/lib/cimi/{model → models}/machine_template_collection.rb +2 -2
- data/lib/cimi/models/network.rb +109 -0
- data/lib/cimi/{model → models}/network_collection.rb +2 -2
- data/lib/cimi/{model → models}/network_configuration.rb +3 -4
- data/lib/cimi/{model → models}/network_configuration_collection.rb +2 -2
- data/lib/cimi/models/network_template.rb +36 -0
- data/lib/cimi/models/network_template_collection.rb +35 -0
- data/lib/cimi/models/routing_group.rb +34 -0
- data/lib/cimi/models/routing_group_collection.rb +34 -0
- data/lib/cimi/models/routing_group_template.rb +34 -0
- data/lib/cimi/models/routing_group_template_collection.rb +35 -0
- data/lib/cimi/{model → models}/schema.rb +0 -0
- data/lib/cimi/{model → models}/volume.rb +4 -4
- data/lib/cimi/{model → models}/volume_collection.rb +2 -2
- data/lib/cimi/{model → models}/volume_configuration.rb +1 -1
- data/lib/cimi/{model → models}/volume_configuration_collection.rb +2 -2
- data/lib/cimi/{model → models}/volume_image.rb +1 -1
- data/lib/cimi/{model → models}/volume_image_collection.rb +2 -2
- data/lib/cimi/{model → models}/volume_template.rb +0 -0
- data/lib/cimi/{model → models}/volume_template_collection.rb +2 -2
- data/lib/cimi/models/vsp.rb +102 -0
- data/lib/cimi/models/vsp_collection.rb +34 -0
- data/lib/cimi/models/vsp_configuration.rb +40 -0
- data/lib/cimi/models/vsp_configuration_collection.rb +34 -0
- data/lib/cimi/models/vsp_template.rb +34 -0
- data/lib/cimi/models/vsp_template_collection.rb +34 -0
- data/lib/cimi/server.rb +27 -549
- data/lib/deltacloud/api.rb +79 -0
- data/lib/deltacloud/collections.rb +54 -0
- data/lib/deltacloud/collections/addresses.rb +91 -0
- data/lib/deltacloud/collections/buckets.rb +273 -0
- data/lib/deltacloud/collections/drivers.rb +51 -0
- data/lib/deltacloud/collections/firewalls.rb +116 -0
- data/lib/deltacloud/collections/hardware_profiles.rb +29 -0
- data/lib/deltacloud/collections/images.rb +73 -0
- data/lib/deltacloud/collections/instance_states.rb +59 -0
- data/lib/deltacloud/collections/instances.rb +113 -0
- data/lib/deltacloud/collections/keys.rb +61 -0
- data/lib/deltacloud/collections/load_balancers.rb +102 -0
- data/lib/deltacloud/collections/metrics.rb +28 -0
- data/lib/deltacloud/collections/realms.rb +28 -0
- data/lib/deltacloud/collections/storage_snapshots.rb +51 -0
- data/lib/deltacloud/collections/storage_volumes.rb +99 -0
- data/lib/deltacloud/core_ext.rb +14 -6
- data/lib/deltacloud/core_ext/string.rb +17 -5
- data/lib/deltacloud/drivers.rb +6 -42
- data/lib/deltacloud/drivers/azure/azure_driver.rb +0 -4
- data/lib/deltacloud/{base_driver → drivers}/base_driver.rb +56 -18
- data/lib/deltacloud/drivers/condor/condor_driver.rb +1 -8
- data/lib/deltacloud/drivers/ec2/ec2_driver.rb +142 -33
- data/lib/deltacloud/drivers/eucalyptus/eucalyptus_driver.rb +2 -6
- data/lib/deltacloud/{base_driver → drivers}/exceptions.rb +25 -2
- data/lib/deltacloud/drivers/features.rb +154 -0
- data/lib/deltacloud/drivers/fgcp/fgcp_client.rb +387 -0
- data/lib/deltacloud/drivers/fgcp/fgcp_driver.rb +1435 -0
- data/lib/deltacloud/drivers/gogrid/gogrid_driver.rb +8 -11
- data/lib/deltacloud/drivers/google/google_driver.rb +2 -5
- data/lib/deltacloud/drivers/mock/data/keys/test-key.yml +28 -0
- data/lib/deltacloud/drivers/mock/mock_client.rb +2 -2
- data/lib/deltacloud/drivers/mock/mock_driver.rb +58 -40
- data/lib/deltacloud/drivers/mock/mock_driver_cimi_methods.rb +145 -0
- data/lib/deltacloud/drivers/opennebula/cloud_client.rb +107 -73
- data/lib/deltacloud/drivers/opennebula/occi_client.rb +285 -145
- data/lib/deltacloud/drivers/opennebula/opennebula_driver.rb +189 -126
- data/lib/deltacloud/drivers/openstack/openstack_driver.rb +427 -8
- data/lib/deltacloud/drivers/rackspace/rackspace_driver.rb +7 -9
- data/lib/deltacloud/drivers/rhevm/rhevm_driver.rb +48 -66
- data/lib/deltacloud/drivers/rimuhosting/rimuhosting_client.rb +44 -51
- data/lib/deltacloud/drivers/rimuhosting/rimuhosting_driver.rb +7 -8
- data/lib/deltacloud/drivers/sbc/sbc_client.rb +1 -1
- data/lib/deltacloud/drivers/sbc/sbc_driver.rb +3 -3
- data/lib/deltacloud/drivers/terremark/terremark_driver.rb +8 -8
- data/lib/deltacloud/drivers/vsphere/vsphere_driver.rb +39 -13
- data/lib/deltacloud/drivers/vsphere/vsphere_filemanager.rb +1 -0
- data/lib/deltacloud/helpers.rb +79 -7
- data/lib/{sinatra/lazy_auth.rb → deltacloud/helpers/auth_helper.rb} +5 -9
- data/lib/deltacloud/helpers/{blob_stream.rb → blob_stream_helper.rb} +7 -7
- data/lib/deltacloud/helpers/deltacloud_helper.rb +286 -0
- data/lib/deltacloud/helpers/driver_helper.rb +58 -0
- data/lib/deltacloud/helpers/rabbit_helper.rb +34 -0
- data/lib/{sinatra/url_for.rb → deltacloud/helpers/url_helper.rb} +31 -9
- data/lib/deltacloud/models.rb +19 -17
- data/lib/deltacloud/models/bucket.rb +4 -0
- data/lib/deltacloud/{hardware_profile.rb → models/hardware_profile.rb} +4 -2
- data/lib/deltacloud/models/image.rb +1 -0
- data/lib/deltacloud/models/instance.rb +4 -2
- data/lib/deltacloud/models/instance_address.rb +4 -0
- data/lib/deltacloud/models/key.rb +4 -0
- data/lib/deltacloud/models/metric.rb +40 -0
- data/lib/deltacloud/{state_machine.rb → models/state_machine.rb} +18 -1
- data/lib/deltacloud/server.rb +41 -1222
- data/lib/deltacloud_rack.rb +79 -0
- data/lib/{cimi/model/network_template.rb → ec2/helpers.rb} +7 -10
- data/lib/{deltacloud/backend_capability.rb → ec2/helpers/errors.rb} +24 -29
- data/lib/ec2/helpers/result.rb +31 -0
- data/lib/ec2/query_parser.rb +152 -0
- data/lib/ec2/server.rb +70 -0
- data/lib/{deltacloud.rb → sinatra.rb} +7 -12
- data/lib/sinatra/rack_accept.rb +13 -7
- data/lib/sinatra/rack_driver_select.rb +1 -1
- data/lib/sinatra/rack_matrix_params.rb +1 -3
- data/public/images/metric.png +0 -0
- data/public/javascripts/jquery.mobile-1.0.1.min.js +177 -0
- data/public/stylesheets/jquery.mobile-1.0.1.min.css +2 -0
- data/public/stylesheets/new.css +10 -0
- data/support/fedora/deltacloud-core.spec +1 -1
- data/tests/api/common.rb +1 -0
- data/tests/api/driver_test.rb +79 -0
- data/tests/api/library_test.rb +48 -0
- data/tests/cimi/features/step_definitions/common_steps.rb +2 -2
- data/tests/cimi/features/step_definitions/machines_steps.rb +5 -4
- data/tests/cimi/features/step_definitions/volumes_steps.rb +8 -8
- data/tests/cimi/features/support/env.rb +33 -11
- data/tests/common.rb +7 -8
- data/tests/drivers/ec2/api_test.rb +19 -0
- data/tests/drivers/ec2/common.rb +23 -0
- data/tests/drivers/ec2/drivers_test.rb +120 -0
- data/tests/drivers/ec2/hardware_profiles_test.rb +224 -0
- data/tests/drivers/ec2/images_test.rb +230 -0
- data/tests/drivers/ec2/instances_test.rb +356 -0
- data/tests/drivers/ec2/keys_test.rb +181 -0
- data/tests/drivers/ec2/realms_test.rb +146 -0
- data/tests/drivers/fgcp/api_test.rb +47 -0
- data/tests/drivers/fgcp/hardware_profiles_test.rb +54 -0
- data/tests/drivers/fgcp/realms_test.rb +42 -0
- data/tests/drivers/{rackspace → fgcp}/setup.rb +5 -6
- data/tests/drivers/google/api_test.rb +10 -26
- data/tests/drivers/google/buckets_test.rb +79 -95
- data/tests/drivers/google/common.rb +54 -0
- data/tests/drivers/mock/api_test.rb +4 -127
- data/tests/drivers/mock/buckets_test.rb +195 -0
- data/tests/drivers/mock/common.rb +7 -0
- data/tests/drivers/mock/drivers_test.rb +123 -0
- data/tests/drivers/mock/hardware_profiles_test.rb +190 -100
- data/tests/drivers/mock/images_test.rb +162 -103
- data/tests/drivers/mock/instances_test.rb +310 -220
- data/tests/drivers/mock/keys_test.rb +161 -0
- data/tests/drivers/mock/realms_test.rb +109 -70
- data/tests/drivers/mock/storage_snapshots_test.rb +114 -0
- data/tests/drivers/mock/storage_volumes_test.rb +122 -0
- data/tests/drivers/openstack/api_test.rb +8 -3
- data/tests/drivers/openstack/common.rb +21 -0
- data/tests/drivers/openstack/hardware_profiles_test.rb +20 -9
- data/tests/drivers/openstack/images_test.rb +11 -5
- data/tests/drivers/openstack/instances_test.rb +61 -16
- data/tests/drivers/openstack/realms_test.rb +11 -7
- data/tests/drivers/rackspace/api_test.rb +7 -2
- data/tests/drivers/rackspace/buckets_test.rb +7 -2
- data/tests/drivers/rackspace/common.rb +16 -0
- data/tests/drivers/rackspace/hardware_profiles_test.rb +7 -2
- data/tests/drivers/rackspace/images_test.rb +7 -2
- data/tests/drivers/rackspace/instances_test.rb +10 -5
- data/tests/drivers/rackspace/realms_test.rb +7 -2
- data/tests/drivers/rhevm/api_test.rb +12 -6
- data/tests/drivers/rhevm/{setup.rb → common.rb} +8 -1
- data/tests/drivers/rhevm/hardware_profiles_test.rb +7 -2
- data/tests/drivers/rhevm/images_test.rb +8 -2
- data/tests/drivers/rhevm/instances_test.rb +7 -2
- data/tests/drivers/rhevm/realms_test.rb +7 -2
- data/tests/minitest_common.rb +58 -0
- data/tests/minitest_common_api_test.rb +115 -0
- data/views/addresses/associate.html.haml +1 -1
- data/views/addresses/index.html.haml +1 -1
- data/views/addresses/show.html.haml +2 -3
- data/views/api/show.html.haml +22 -9
- data/views/api/show.xml.haml +8 -7
- data/views/blobs/show.xml.haml +7 -4
- data/views/buckets/new.html.haml +2 -2
- data/views/cimi/errors/401.xml.haml +1 -1
- data/views/error.html.haml +3 -3
- data/views/errors/400.html.haml +1 -1
- data/views/errors/400.xml.haml +1 -2
- data/views/errors/401.html.haml +8 -7
- data/views/errors/401.xml.haml +1 -1
- data/views/errors/404.xml.haml +1 -0
- data/views/errors/500.xml.haml +4 -2
- data/views/{cimi/errors/403.html.haml → errors/501.html.haml} +4 -2
- data/views/errors/501.xml.haml +1 -0
- data/views/errors/502.xml.haml +1 -7
- data/views/{cimi/errors/500.html.haml → errors/504.html.haml} +0 -0
- data/views/errors/504.xml.haml +1 -0
- data/views/firewalls/new.html.haml +2 -2
- data/views/firewalls/new_rule.html.haml +1 -1
- data/views/firewalls/show.html.haml +1 -1
- data/views/hardware_profiles/index.html.haml +3 -1
- data/views/hardware_profiles/index.xml.haml +2 -2
- data/views/hardware_profiles/show.html.haml +3 -3
- data/views/hardware_profiles/show.xml.haml +3 -3
- data/views/images/show.html.haml +5 -0
- data/views/images/show.xml.haml +6 -1
- data/views/instance_states/show.html.haml +1 -1
- data/views/instances/index.html.haml +1 -1
- data/views/instances/new.html.haml +54 -39
- data/views/instances/run_command.html.haml +24 -15
- data/views/instances/show.html.haml +7 -3
- data/views/instances/show.xml.haml +2 -2
- data/views/keys/show.xml.haml +1 -0
- data/views/layout.html.haml +5 -9
- data/views/load_balancers/show.html.haml +12 -6
- data/views/metrics/index.html.haml +13 -0
- data/views/metrics/index.xml.haml +5 -0
- data/views/metrics/show.html.haml +23 -0
- data/views/metrics/show.xml.haml +9 -0
- data/views/realms/show.xml.haml +2 -1
- data/views/root/index.html.haml +1 -1
- data/views/storage_snapshots/show.html.haml +1 -1
- data/views/storage_snapshots/show.xml.haml +1 -0
- data/views/storage_volumes/attach.html.haml +1 -2
- data/views/storage_volumes/index.html.haml +1 -1
- data/views/storage_volumes/new.html.haml +22 -16
- data/views/storage_volumes/show.html.haml +10 -4
- data/views/storage_volumes/show.xml.haml +3 -4
- metadata +547 -519
- data/DISCLAIMER +0 -8
- data/lib/cimi/model.rb +0 -52
- data/lib/cimi/model/network.rb +0 -69
- data/lib/deltacloud/base_driver.rb +0 -18
- data/lib/deltacloud/base_driver/features.rb +0 -262
- data/lib/deltacloud/base_driver/mock_driver.rb +0 -78
- data/lib/deltacloud/drivers/ec2/ec2_mock_driver.rb +0 -186
- data/lib/deltacloud/drivers/rhevm/rhevm_client.rb +0 -521
- data/lib/deltacloud/helpers/application_helper.rb +0 -267
- data/lib/deltacloud/helpers/hardware_profiles_helper.rb +0 -50
- data/lib/deltacloud/helpers/json_helper.rb +0 -31
- data/lib/deltacloud/method_serializer.rb +0 -83
- data/lib/deltacloud/validation.rb +0 -107
- data/lib/sinatra/rabbit.rb +0 -441
- data/lib/sinatra/rack_runtime.rb +0 -47
- data/lib/sinatra/rack_syslog.rb +0 -86
- data/lib/sinatra/sinatra_verbose.rb +0 -73
- data/lib/sinatra/static_assets.rb +0 -99
- data/public/javascripts/jquery.mobile-1.0rc1.min.js +0 -170
- data/public/stylesheets/jquery.mobile-1.0rc1.min.css +0 -12
- data/tests/drivers/google/setup.rb +0 -38
- data/tests/drivers/mock/instance_states_test.rb +0 -71
- data/tests/drivers/mock/setup.rb +0 -3
- data/tests/drivers/mock/url_for_test.rb +0 -67
- data/tests/drivers/openstack/setup.rb +0 -20
- data/views/cimi/errors/400.html.haml +0 -41
- data/views/cimi/errors/401.html.haml +0 -41
- data/views/cimi/errors/404.html.haml +0 -29
- data/views/cimi/errors/405.html.haml +0 -29
- data/views/cimi/errors/502.html.haml +0 -43
- data/views/cimi/errors/backend_capability_failure.html.haml +0 -29
@@ -0,0 +1,58 @@
|
|
1
|
+
# Licensed to the Apache Software Foundation (ASF) under one or more
|
2
|
+
# contributor license agreements. See the NOTICE file distributed with
|
3
|
+
# this work for additional information regarding copyright ownership. The
|
4
|
+
# ASF licenses this file to you under the Apache License, Version 2.0 (the
|
5
|
+
# "License"); you may not use this file except in compliance with the
|
6
|
+
# License. You may obtain a copy of the License 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, WITHOUT
|
12
|
+
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
13
|
+
# License for the specific language governing permissions and limitations
|
14
|
+
# under the License.
|
15
|
+
|
16
|
+
module Deltacloud::Helpers
|
17
|
+
|
18
|
+
module Drivers
|
19
|
+
|
20
|
+
def driver_symbol
|
21
|
+
driver_name.to_sym
|
22
|
+
end
|
23
|
+
|
24
|
+
def driver_name
|
25
|
+
Thread.current[:driver] ||= ENV['API_DRIVER']
|
26
|
+
end
|
27
|
+
|
28
|
+
def driver_class_name
|
29
|
+
driver_name.camelize
|
30
|
+
end
|
31
|
+
|
32
|
+
def driver_source_name
|
33
|
+
File.join('..', 'drivers', driver_name, driver_name + '_driver.rb')
|
34
|
+
end
|
35
|
+
|
36
|
+
def driver_class
|
37
|
+
begin
|
38
|
+
m = Deltacloud::Drivers.const_get(driver_class_name)
|
39
|
+
m.const_get(driver_class_name + "Driver").new
|
40
|
+
rescue NameError
|
41
|
+
raise "[ERROR] The driver class name is not defined as #{driver_class_name}Driver"
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def driver
|
46
|
+
$:.unshift File.join(File.dirname(__FILE__), '..', '..')
|
47
|
+
begin
|
48
|
+
require_relative driver_source_name
|
49
|
+
driver_class
|
50
|
+
rescue LoadError => e
|
51
|
+
raise "[ERROR] The driver '#{driver_name}' is unknown or not installed (#{driver_source_name})\n" +
|
52
|
+
"\n#{e.message}\n"
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
end
|
57
|
+
|
58
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
# Licensed to the Apache Software Foundation (ASF) under one or more
|
2
|
+
# contributor license agreements. See the NOTICE file distributed with
|
3
|
+
# this work for additional information regarding copyright ownership. The
|
4
|
+
# ASF licenses this file to you under the Apache License, Version 2.0 (the
|
5
|
+
# "License"); you may not use this file except in compliance with the
|
6
|
+
# License. You may obtain a copy of the License 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, WITHOUT
|
12
|
+
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
13
|
+
# License for the specific language governing permissions and limitations
|
14
|
+
# under the License.
|
15
|
+
|
16
|
+
|
17
|
+
Sinatra::Rabbit::Collection.class_eval do
|
18
|
+
|
19
|
+
def self.standard_index_operation(opts={})
|
20
|
+
collection_name = @collection_name
|
21
|
+
operation :index, :with_capability => opts[:capability] || collection_name do
|
22
|
+
control { filter_all collection_name }
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
def self.standard_show_operation(opts={})
|
27
|
+
collection_name = @collection_name
|
28
|
+
operation :show, :with_capability => opts[:capability] || collection_name do
|
29
|
+
control { show collection_name.to_s.singularize.intern }
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
end
|
34
|
+
|
@@ -24,11 +24,31 @@
|
|
24
24
|
# OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
|
25
25
|
# USE OR OTHER DEALINGS IN THE SOFTWARE.
|
26
26
|
|
27
|
-
require 'uri'
|
28
|
-
|
29
27
|
module Sinatra
|
30
28
|
module UrlForHelper
|
31
29
|
|
30
|
+
require 'uri'
|
31
|
+
|
32
|
+
def method_missing(name, *args)
|
33
|
+
if name.to_s =~ /^([\w\_]+)_url$/
|
34
|
+
if args.size > 0
|
35
|
+
t = $1
|
36
|
+
if t.match(/^(stop|reboot|start|attach|detach)_/)
|
37
|
+
action = $1
|
38
|
+
api_url_for(t.pluralize.split('_').last + '/' + args.first + '/' + action, :full)
|
39
|
+
elsif t.match(/^(destroy|update)_/)
|
40
|
+
api_url_for(t.pluralize.split('_').last + '/' + args.first, :full)
|
41
|
+
else
|
42
|
+
api_url_for(t.pluralize, :full) + '/' + "#{args.first}"
|
43
|
+
end
|
44
|
+
else
|
45
|
+
api_url_for($1, :full)
|
46
|
+
end
|
47
|
+
else
|
48
|
+
super
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
32
52
|
def api_url_for(url_fragment, mode=:path_only)
|
33
53
|
matrix_params = ''
|
34
54
|
if request.params['api']
|
@@ -36,7 +56,11 @@ module Sinatra
|
|
36
56
|
matrix_params += ";driver=%s" % request.params['api']['driver'] if request.params['api']['driver']
|
37
57
|
end
|
38
58
|
url_fragment = "/#{url_fragment}" unless url_fragment =~ /^\// # There is no need to prefix URI with '/'
|
39
|
-
|
59
|
+
if mode == :path_only
|
60
|
+
url_for "#{settings.root_url}#{matrix_params}#{url_fragment}", mode
|
61
|
+
else
|
62
|
+
url_for "#{matrix_params}#{url_fragment}", :full
|
63
|
+
end
|
40
64
|
end
|
41
65
|
|
42
66
|
# Construct a link to +url_fragment+, which should be given relative to
|
@@ -55,7 +79,7 @@ module Sinatra
|
|
55
79
|
def url_for url_fragment, mode=:path_only
|
56
80
|
case mode
|
57
81
|
when :path_only
|
58
|
-
base = request.script_name
|
82
|
+
base = request.script_name.empty? ? Deltacloud[ENV['API_FRONTEND'] || :deltacloud].root_url : request.script_name
|
59
83
|
when :full
|
60
84
|
scheme = request.scheme
|
61
85
|
port = request.port
|
@@ -72,11 +96,12 @@ module Sinatra
|
|
72
96
|
else
|
73
97
|
port = ":#{port}"
|
74
98
|
end
|
75
|
-
base = "#{scheme}://#{request_host}#{port}#{request.script_name}"
|
99
|
+
base = "#{scheme}://#{request_host}#{port}#{request.script_name.empty? ? Deltacloud[ENV['API_FRONTEND'] || :deltacloud].root_url : request.script_name}"
|
76
100
|
else
|
77
101
|
raise TypeError, "Unknown url_for mode #{mode}"
|
78
102
|
end
|
79
|
-
|
103
|
+
uri_parser = URI.const_defined?(:Parser) ? URI::Parser.new : URI
|
104
|
+
url_escape = uri_parser.escape(url_fragment)
|
80
105
|
# Don't add the base fragment if url_for gets called more than once
|
81
106
|
# per url or the url_fragment passed in is an absolute url
|
82
107
|
if url_escape.match(/^#{base}/) or url_escape.match(/^http/)
|
@@ -87,7 +112,4 @@ module Sinatra
|
|
87
112
|
end
|
88
113
|
end
|
89
114
|
|
90
|
-
|
91
|
-
|
92
|
-
helpers UrlForHelper
|
93
115
|
end
|
data/lib/deltacloud/models.rb
CHANGED
@@ -1,4 +1,3 @@
|
|
1
|
-
#
|
2
1
|
# Licensed to the Apache Software Foundation (ASF) under one or more
|
3
2
|
# contributor license agreements. See the NOTICE file distributed with
|
4
3
|
# this work for additional information regarding copyright ownership. The
|
@@ -14,19 +13,22 @@
|
|
14
13
|
# License for the specific language governing permissions and limitations
|
15
14
|
# under the License.
|
16
15
|
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
16
|
+
require_relative 'models/base_model'
|
17
|
+
require_relative 'models/address'
|
18
|
+
require_relative 'models/blob'
|
19
|
+
require_relative 'models/bucket'
|
20
|
+
require_relative 'models/firewall'
|
21
|
+
require_relative 'models/firewall_rule'
|
22
|
+
require_relative 'models/hardware_profile'
|
23
|
+
require_relative 'models/image'
|
24
|
+
require_relative 'models/instance'
|
25
|
+
require_relative 'models/instance_address'
|
26
|
+
require_relative 'models/instance_profile'
|
27
|
+
require_relative 'models/key'
|
28
|
+
require_relative 'models/load_balancer'
|
29
|
+
require_relative 'models/metric'
|
30
|
+
require_relative 'models/provider'
|
31
|
+
require_relative 'models/realm'
|
32
|
+
require_relative 'models/state_machine'
|
33
|
+
require_relative 'models/storage_snapshot'
|
34
|
+
require_relative 'models/storage_volume'
|
@@ -22,7 +22,7 @@ module Deltacloud
|
|
22
22
|
:storage => "GB",
|
23
23
|
:architecture => "label",
|
24
24
|
:cpu => "count"
|
25
|
-
}
|
25
|
+
} unless defined?(UNITS)
|
26
26
|
|
27
27
|
def self.unit(name)
|
28
28
|
UNITS[name]
|
@@ -90,7 +90,9 @@ module Deltacloud
|
|
90
90
|
end
|
91
91
|
|
92
92
|
def to_param
|
93
|
-
|
93
|
+
if defined? Sinatra::Rabbit
|
94
|
+
Sinatra::Rabbit::Param.new([param, :string, :optional, []])
|
95
|
+
end
|
94
96
|
end
|
95
97
|
|
96
98
|
def include?(v)
|
@@ -16,8 +16,6 @@
|
|
16
16
|
|
17
17
|
class Instance < BaseModel
|
18
18
|
|
19
|
-
include ApplicationHelper
|
20
|
-
|
21
19
|
attr_accessor :owner_id
|
22
20
|
attr_accessor :image_id
|
23
21
|
attr_accessor :name
|
@@ -36,6 +34,10 @@ class Instance < BaseModel
|
|
36
34
|
attr_accessor :firewalls
|
37
35
|
attr_accessor :storage_volumes
|
38
36
|
|
37
|
+
def storage_volumes
|
38
|
+
@storage_volumes || []
|
39
|
+
end
|
40
|
+
|
39
41
|
def can_create_image?
|
40
42
|
self.create_image
|
41
43
|
end
|
@@ -0,0 +1,40 @@
|
|
1
|
+
# Licensed to the Apache Software Foundation (ASF) under one or more
|
2
|
+
# contributor license agreements. See the NOTICE file distributed with
|
3
|
+
# this work for additional information regarding copyright ownership. The
|
4
|
+
# ASF licenses this file to you under the Apache License, Version 2.0 (the
|
5
|
+
# "License"); you may not use this file except in compliance with the
|
6
|
+
# License. You may obtain a copy of the License 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, WITHOUT
|
12
|
+
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
13
|
+
# License for the specific language governing permissions and limitations
|
14
|
+
# under the License.
|
15
|
+
|
16
|
+
class Metric < BaseModel
|
17
|
+
|
18
|
+
attr_accessor :entity
|
19
|
+
attr_accessor :properties
|
20
|
+
|
21
|
+
def unknown?
|
22
|
+
true if self.entity == :unknown
|
23
|
+
end
|
24
|
+
|
25
|
+
def add_property(name, values=nil)
|
26
|
+
self.properties ||= []
|
27
|
+
return self if self.properties.any? { |p| p.name == name }
|
28
|
+
self.properties << Property.new(name, values)
|
29
|
+
self
|
30
|
+
end
|
31
|
+
|
32
|
+
class Property
|
33
|
+
attr_accessor :name, :values
|
34
|
+
|
35
|
+
def initialize(name, values=nil)
|
36
|
+
@name, @values = name, values
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
end
|
@@ -18,7 +18,10 @@ module Deltacloud
|
|
18
18
|
class StateMachine
|
19
19
|
|
20
20
|
attr_reader :states
|
21
|
-
|
21
|
+
|
22
|
+
def initialize(opts={}, &block)
|
23
|
+
@all_states = opts[:all_states]
|
24
|
+
@all_actions = opts[:all_actions]
|
22
25
|
@states = []
|
23
26
|
instance_eval &block if block
|
24
27
|
end
|
@@ -32,6 +35,9 @@ module Deltacloud
|
|
32
35
|
end
|
33
36
|
|
34
37
|
def state(name)
|
38
|
+
unless valid_state_name?(name)
|
39
|
+
raise "State '#{name}' not in list of allowed states"
|
40
|
+
end
|
35
41
|
state = @states.find{|e| e.name == name.to_sym}
|
36
42
|
if ( state.nil? )
|
37
43
|
state = State.new( self, name.to_sym )
|
@@ -40,6 +46,14 @@ module Deltacloud
|
|
40
46
|
state
|
41
47
|
end
|
42
48
|
|
49
|
+
def valid_state_name?(name)
|
50
|
+
@all_states.nil? || @all_states.include?(name.to_sym)
|
51
|
+
end
|
52
|
+
|
53
|
+
def valid_action_name?(name)
|
54
|
+
@all_actions.nil? || @all_actions.include?(name.to_sym)
|
55
|
+
end
|
56
|
+
|
43
57
|
def method_missing(sym,*args)
|
44
58
|
return state( sym ) if ( args.empty? )
|
45
59
|
super( sym, *args )
|
@@ -90,6 +104,9 @@ module Deltacloud
|
|
90
104
|
end
|
91
105
|
|
92
106
|
def on(action)
|
107
|
+
unless @machine.valid_action_name?(action)
|
108
|
+
raise "Action '#{action}' not in list of allowed actions"
|
109
|
+
end
|
93
110
|
@action = action
|
94
111
|
end
|
95
112
|
|
data/lib/deltacloud/server.rb
CHANGED
@@ -13,1246 +13,65 @@
|
|
13
13
|
# License for the specific language governing permissions and limitations
|
14
14
|
# under the License.
|
15
15
|
|
16
|
-
require '
|
17
|
-
require '
|
16
|
+
require 'rubygems'
|
17
|
+
require 'crack'
|
18
18
|
require 'json'
|
19
|
-
require '
|
20
|
-
require 'sinatra/static_assets'
|
21
|
-
require 'sinatra/rabbit'
|
22
|
-
require 'sinatra/lazy_auth'
|
23
|
-
require 'erb'
|
19
|
+
require 'yaml'
|
24
20
|
require 'haml'
|
25
|
-
require '
|
26
|
-
require 'sinatra/
|
27
|
-
require 'sinatra/rack_driver_select'
|
28
|
-
require 'sinatra/rack_runtime'
|
29
|
-
require 'sinatra/rack_etag'
|
30
|
-
require 'sinatra/rack_date'
|
31
|
-
require 'sinatra/rack_matrix_params'
|
32
|
-
require 'sinatra/rack_syslog'
|
33
|
-
|
34
|
-
set :version, '0.5.0'
|
35
|
-
|
36
|
-
include Deltacloud::Drivers
|
37
|
-
set :drivers, Proc.new { driver_config }
|
38
|
-
|
39
|
-
Sinatra::Application.register Rack::RespondTo
|
40
|
-
|
41
|
-
use Rack::ETag
|
42
|
-
use Rack::Runtime
|
43
|
-
use Rack::MatrixParams
|
44
|
-
use Rack::DriverSelect
|
45
|
-
use Rack::MediaType
|
46
|
-
use Rack::Date
|
47
|
-
|
48
|
-
configure do
|
49
|
-
set :root_url, "/api"
|
50
|
-
set :views, File::join($top_srcdir, 'views')
|
51
|
-
# NOTE: Change :public to :public_folder once we update sinatra to 1.3
|
52
|
-
# set :public_folder, File::join($top_srcdir, 'public')
|
53
|
-
if settings.respond_to? :public_folder
|
54
|
-
set :public_folder, File::join($top_srcdir, 'public')
|
55
|
-
else
|
56
|
-
set :public, File::join($top_srcdir, 'public')
|
57
|
-
end
|
58
|
-
# Try to load the driver on startup to fail early if there are issues
|
59
|
-
driver
|
60
|
-
end
|
61
|
-
|
62
|
-
configure :production do
|
63
|
-
use Rack::SyslogLogger
|
64
|
-
disable :logging
|
65
|
-
enable :show_errors
|
66
|
-
set :dump_errors, false
|
67
|
-
$stdout = SyslogFile.new
|
68
|
-
$stderr = $stdout
|
69
|
-
end
|
70
|
-
|
71
|
-
configure :development do
|
72
|
-
# So we can just use puts for logging
|
73
|
-
set :raise_errors => false
|
74
|
-
set :show_exceptions, false
|
75
|
-
$stdout.sync = true
|
76
|
-
$stderr.sync = true
|
77
|
-
end
|
78
|
-
|
79
|
-
# You could use $API_HOST environment variable to change your hostname to
|
80
|
-
# whatever you want (eg. if you running API behind NAT)
|
81
|
-
HOSTNAME=ENV['API_HOST'] ? ENV['API_HOST'] : nil
|
82
|
-
|
83
|
-
error do
|
84
|
-
report_error
|
85
|
-
end
|
86
|
-
|
87
|
-
before do
|
88
|
-
# Respond with 400, If we don't get a http Host header,
|
89
|
-
halt 400, "Unable to find HTTP Host header" if @env['HTTP_HOST'] == nil
|
90
|
-
end
|
91
|
-
|
92
|
-
after do
|
93
|
-
headers 'Server' => 'Apache-Deltacloud/' + settings.version
|
94
|
-
end
|
95
|
-
|
96
|
-
# Redirect to /api
|
97
|
-
get '/' do redirect settings.root_url, 301; end
|
98
|
-
|
99
|
-
|
100
|
-
# Generate a root route for API docs
|
101
|
-
get "#{settings.root_url}/docs\/?" do
|
102
|
-
respond_to do |format|
|
103
|
-
format.html { haml :'docs/index' }
|
104
|
-
format.xml { haml :'docs/index' }
|
105
|
-
end
|
106
|
-
end
|
107
|
-
|
108
|
-
get "#{settings.root_url}\/?" do
|
109
|
-
if params[:force_auth]
|
110
|
-
return [401, 'Authentication failed'] unless driver.valid_credentials?(credentials)
|
111
|
-
end
|
112
|
-
@collections = [:drivers] + driver.supported_collections
|
113
|
-
@driver_name = driver.name unless driver.name.to_sym == DRIVER
|
114
|
-
@providers = driver.configured_providers
|
115
|
-
respond_to do |format|
|
116
|
-
format.xml { haml :"api/show" }
|
117
|
-
format.json do
|
118
|
-
{ :api => {
|
119
|
-
:version => settings.version,
|
120
|
-
:driver => driver_symbol,
|
121
|
-
:links => entry_points.collect do |l|
|
122
|
-
{ :rel => l[0], :href => l[1] }.merge(json_features_for_entrypoint(l))
|
123
|
-
end
|
124
|
-
}
|
125
|
-
}.to_json
|
126
|
-
end
|
127
|
-
format.html { haml :"api/show" }
|
128
|
-
end
|
129
|
-
end
|
130
|
-
|
131
|
-
post "#{settings.root_url}\/?" do
|
132
|
-
p = {}
|
133
|
-
["provider", "driver"].each { |k| p[k] = params[k] if params[k] }
|
134
|
-
p.delete("provider") if p["provider"] == "default"
|
135
|
-
q = p.map { |k,v| "#{k}=#{v}" }.join(";")
|
136
|
-
q = ";" + q unless q.empty?
|
137
|
-
redirect "#{settings.root_url}#{q}", 301
|
138
|
-
end
|
139
|
-
|
140
|
-
# Rabbit DSL
|
141
|
-
|
142
|
-
collection :drivers do
|
143
|
-
global!
|
144
|
-
|
145
|
-
description <<EOS
|
146
|
-
List all the drivers supported by this server.
|
147
|
-
EOS
|
148
|
-
|
149
|
-
operation :index do
|
150
|
-
description "List all drivers"
|
151
|
-
control do
|
152
|
-
@drivers = settings.drivers
|
153
|
-
respond_to do |format|
|
154
|
-
format.xml { haml :"drivers/index" }
|
155
|
-
format.json { @drivers.to_json }
|
156
|
-
format.html { haml :"drivers/index" }
|
157
|
-
end
|
158
|
-
end
|
159
|
-
end
|
160
|
-
|
161
|
-
operation :show do
|
162
|
-
description "Show details for a driver"
|
163
|
-
param :id, :string
|
164
|
-
control do
|
165
|
-
@name = params[:id].to_sym
|
166
|
-
if driver_symbol == @name
|
167
|
-
@providers = driver.providers(credentials) if driver.respond_to? :providers
|
168
|
-
end
|
169
|
-
@driver = settings.drivers[@name]
|
170
|
-
return [404, "Driver #{@name} not found"] unless @driver
|
171
|
-
respond_to do |format|
|
172
|
-
format.xml { haml :"drivers/show" }
|
173
|
-
format.json { @driver.to_json }
|
174
|
-
format.html { haml :"drivers/show" }
|
175
|
-
end
|
176
|
-
end
|
177
|
-
end
|
178
|
-
end
|
179
|
-
|
180
|
-
collection :realms do
|
181
|
-
description <<END
|
182
|
-
Within a cloud provider a realm represents a boundary containing resources.
|
183
|
-
The exact definition of a realm is left to the cloud provider.
|
184
|
-
In some cases, a realm may represent different datacenters, different continents,
|
185
|
-
or different pools of resources within a single datacenter.
|
186
|
-
A cloud provider may insist that resources must all exist within a single realm in
|
187
|
-
order to cooperate. For instance, storage volumes may only be allowed to be mounted to
|
188
|
-
instances within the same realm.
|
189
|
-
END
|
190
|
-
|
191
|
-
operation :index do
|
192
|
-
description <<END
|
193
|
-
Operation will list all available realms. Realms can be filtered using
|
194
|
-
the "architecture" parameter.
|
195
|
-
END
|
196
|
-
with_capability :realms
|
197
|
-
param :id, :string
|
198
|
-
param :architecture, :string, :optional, [ 'i386', 'x86_64' ]
|
199
|
-
control { filter_all(:realms) }
|
200
|
-
end
|
201
|
-
|
202
|
-
#FIXME: It always shows whole list
|
203
|
-
operation :show do
|
204
|
-
description 'Show an realm identified by "id" parameter.'
|
205
|
-
with_capability :realm
|
206
|
-
param :id, :string, :required
|
207
|
-
control { show(:realm) }
|
208
|
-
end
|
209
|
-
|
210
|
-
end
|
211
|
-
|
212
|
-
collection :images do
|
213
|
-
description <<END
|
214
|
-
An image is a platonic form of a machine. Images are not directly executable,
|
215
|
-
but are a template for creating actual instances of machines.
|
216
|
-
END
|
217
|
-
|
218
|
-
operation :new do
|
219
|
-
description "Form to create a new image resource"
|
220
|
-
param :instance_id, :string, "An instance from which the new image will be created from"
|
221
|
-
control do
|
222
|
-
@instance = Instance.new( :id => params[:instance_id] )
|
223
|
-
respond_to do |format|
|
224
|
-
format.html { haml :"images/new" }
|
225
|
-
end
|
226
|
-
end
|
227
|
-
end
|
228
|
-
|
229
|
-
operation :index do
|
230
|
-
description <<END
|
231
|
-
The images collection will return a set of all images
|
232
|
-
available to the current use. Images can be filtered using the
|
233
|
-
"owner_id" and "architecture" parameters.
|
234
|
-
END
|
235
|
-
with_capability :images
|
236
|
-
param :id, :string
|
237
|
-
param :architecture, :string, :optional
|
238
|
-
control { filter_all(:images) }
|
239
|
-
end
|
240
|
-
|
241
|
-
operation :show do
|
242
|
-
description 'Show an image identified by "id" parameter.'
|
243
|
-
with_capability :image
|
244
|
-
param :id, :string, :required
|
245
|
-
control { show(:image) }
|
246
|
-
end
|
247
|
-
|
248
|
-
operation :create do
|
249
|
-
description 'Create image from instance'
|
250
|
-
with_capability :create_image
|
251
|
-
param :instance_id, :string, :required
|
252
|
-
param :name, :string, :optional
|
253
|
-
param :description, :string, :optional
|
254
|
-
control do
|
255
|
-
@image = driver.create_image(credentials, {
|
256
|
-
:id => params[:instance_id],
|
257
|
-
:name => params[:name],
|
258
|
-
:description => params[:description]
|
259
|
-
})
|
260
|
-
status 201 # Created
|
261
|
-
response['Location'] = image_url(@image.id)
|
262
|
-
respond_to do |format|
|
263
|
-
format.xml { haml :"images/show" }
|
264
|
-
format.json { convert_to_json(:image, @image) }
|
265
|
-
format.html { haml :"images/show" }
|
266
|
-
end
|
267
|
-
end
|
268
|
-
end
|
269
|
-
|
270
|
-
operation :destroy do
|
271
|
-
description "Remove specified image from collection"
|
272
|
-
with_capability :destroy_image
|
273
|
-
param :id, :string, :required
|
274
|
-
control do
|
275
|
-
driver.destroy_image(credentials, params[:id])
|
276
|
-
status 204
|
277
|
-
respond_to do |format|
|
278
|
-
format.xml
|
279
|
-
format.json
|
280
|
-
format.html { redirect(images_url) }
|
281
|
-
end
|
282
|
-
end
|
283
|
-
end
|
284
|
-
|
285
|
-
end
|
286
|
-
|
287
|
-
collection :instance_states do
|
288
|
-
description "The possible states of an instance, and how to traverse between them "
|
289
|
-
|
290
|
-
operation :index do
|
291
|
-
control do
|
292
|
-
@machine = driver.instance_state_machine
|
293
|
-
respond_to do |format|
|
294
|
-
format.xml { haml :'instance_states/show', :layout => false }
|
295
|
-
format.json do
|
296
|
-
out = []
|
297
|
-
@machine.states.each do |state|
|
298
|
-
transitions = state.transitions.collect do |t|
|
299
|
-
t.automatically? ? {:to => t.destination, :auto => 'true'} : {:to => t.destination, :action => t.action}
|
300
|
-
end
|
301
|
-
out << { :name => state, :transitions => transitions }
|
302
|
-
end
|
303
|
-
out.to_json
|
304
|
-
end
|
305
|
-
format.html { haml :'instance_states/show'}
|
306
|
-
format.gv { erb :"instance_states/show" }
|
307
|
-
format.png do
|
308
|
-
# Trick respond_to into looking up the right template for the
|
309
|
-
# graphviz file
|
310
|
-
gv = erb(:"instance_states/show")
|
311
|
-
png = ''
|
312
|
-
cmd = 'dot -Kdot -Gpad="0.2,0.2" -Gsize="5.0,8.0" -Gdpi="180" -Tpng'
|
313
|
-
Open3.popen3( cmd ) do |stdin, stdout, stderr|
|
314
|
-
stdin.write( gv )
|
315
|
-
stdin.close()
|
316
|
-
png = stdout.read
|
317
|
-
end
|
318
|
-
content_type 'image/png'
|
319
|
-
png
|
320
|
-
end
|
321
|
-
end
|
322
|
-
end
|
323
|
-
end
|
324
|
-
end
|
325
|
-
|
326
|
-
get "#{settings.root_url}/instances/:id/run" do
|
327
|
-
@instance = driver.instance(credentials, :id => params[:id])
|
328
|
-
respond_to do |format|
|
329
|
-
format.html { haml :"instances/run_command" }
|
330
|
-
end
|
331
|
-
end
|
332
|
-
|
333
|
-
collection :load_balancers do
|
334
|
-
description "Load balancers"
|
335
|
-
|
336
|
-
operation :new do
|
337
|
-
description "Form to create a new load balancer"
|
338
|
-
control do
|
339
|
-
@realms = driver.realms(credentials)
|
340
|
-
@instances = driver.instances(credentials) if driver_has_feature?(:register_instance, :load_balancers)
|
341
|
-
respond_to do |format|
|
342
|
-
format.html { haml :"load_balancers/new" }
|
343
|
-
end
|
344
|
-
end
|
345
|
-
end
|
346
|
-
|
347
|
-
operation :index do
|
348
|
-
description "List of all active load balancers"
|
349
|
-
control do
|
350
|
-
filter_all :load_balancers
|
351
|
-
end
|
352
|
-
end
|
353
|
-
|
354
|
-
operation :show do
|
355
|
-
description "Show details about given load balancer"
|
356
|
-
param :id, :string, :required
|
357
|
-
control { show :load_balancer }
|
358
|
-
end
|
359
|
-
|
360
|
-
operation :create do
|
361
|
-
description "Create a new load balancer"
|
362
|
-
param :name, :string, :required
|
363
|
-
param :realm_id, :string, :required
|
364
|
-
param :listener_protocol, :string, :required, ['HTTP', 'TCP']
|
365
|
-
param :listener_balancer_port, :string, :required
|
366
|
-
param :listener_instance_port, :string, :required
|
367
|
-
control do
|
368
|
-
@load_balancer = driver.create_load_balancer(credentials, params)
|
369
|
-
status 201 # Created
|
370
|
-
response['Location'] = load_balancer_url(@instance.id)
|
371
|
-
respond_to do |format|
|
372
|
-
format.xml { haml :"load_balancers/show" }
|
373
|
-
format.json { convert_to_json(:load_balancer, @load_balancer) }
|
374
|
-
format.html { haml :"load_balancers/show" }
|
375
|
-
end
|
376
|
-
end
|
377
|
-
end
|
378
|
-
|
379
|
-
operation :register, :method => :post, :member => true do
|
380
|
-
description "Add instance to loadbalancer"
|
381
|
-
param :id, :string, :required
|
382
|
-
param :instance_id, :string, :required
|
383
|
-
control do
|
384
|
-
driver.lb_register_instance(credentials, params)
|
385
|
-
status 204
|
386
|
-
respond_to do |format|
|
387
|
-
format.xml
|
388
|
-
format.json
|
389
|
-
format.html { redirect(load_balancer_url(params[:id])) }
|
390
|
-
end
|
391
|
-
end
|
392
|
-
end
|
393
|
-
|
394
|
-
operation :unregister, :method => :post, :member => true do
|
395
|
-
description "Remove instance from loadbalancer"
|
396
|
-
param :id, :string, :required
|
397
|
-
param :instance_id, :string, :required
|
398
|
-
control do
|
399
|
-
driver.lb_unregister_instance(credentials, params)
|
400
|
-
status 204
|
401
|
-
respond_to do |format|
|
402
|
-
format.xml
|
403
|
-
format.json
|
404
|
-
format.html { redirect(load_balancer_url(params[:id])) }
|
405
|
-
end
|
406
|
-
end
|
407
|
-
end
|
408
|
-
|
409
|
-
operation :destroy do
|
410
|
-
description "Destroy given load balancer"
|
411
|
-
param :id, :string, :required
|
412
|
-
control do
|
413
|
-
driver.destroy_load_balancer(credentials, params[:id])
|
414
|
-
status 204
|
415
|
-
respond_to do |format|
|
416
|
-
format.xml
|
417
|
-
format.json
|
418
|
-
format.html { redirect(load_balancers_url) }
|
419
|
-
end
|
420
|
-
end
|
421
|
-
end
|
422
|
-
|
423
|
-
end
|
424
|
-
|
425
|
-
|
426
|
-
collection :instances do
|
427
|
-
description <<END
|
428
|
-
An instance is a concrete machine realized from an image.
|
429
|
-
The images collection may be obtained by following the link from the primary entry-point.
|
430
|
-
END
|
431
|
-
|
432
|
-
operation :new do
|
433
|
-
description "Form for creating a new instance resource"
|
434
|
-
param :image_id, :string, "Image from which will be the new instance created from"
|
435
|
-
param :realm_id, :string, :optional
|
436
|
-
if driver_has_feature? :authentication_key
|
437
|
-
param :authentication_key, :string, :optional
|
438
|
-
end
|
439
|
-
if driver_has_feature? :firewalls
|
440
|
-
param :firewalls, :string, :optional
|
441
|
-
end
|
442
|
-
control do
|
443
|
-
@instance = Instance.new( { :id=>params[:id], :image_id=>params[:image_id] } )
|
444
|
-
@image = Image.new( :id => params[:image_id] )
|
445
|
-
@hardware_profiles = driver.hardware_profiles(credentials, :architecture => @image.architecture )
|
446
|
-
@realms = [Realm.new(:id => params[:realm_id])] if params[:realm_id]
|
447
|
-
@realms ||= driver.realms(credentials)
|
448
|
-
@keys = driver.keys(credentials) if driver_has_feature?(:authentication_key)
|
449
|
-
@firewalls = driver.firewalls(credentials) if driver_has_feature?(:firewalls)
|
450
|
-
respond_to do |format|
|
451
|
-
format.html do
|
452
|
-
haml :'instances/new'
|
453
|
-
end
|
454
|
-
end
|
455
|
-
end
|
456
|
-
end
|
457
|
-
|
458
|
-
operation :index do
|
459
|
-
description "List all instances."
|
460
|
-
with_capability :instances
|
461
|
-
param :id, :string, :optional
|
462
|
-
param :state, :string, :optional
|
463
|
-
control { filter_all(:instances) }
|
464
|
-
end
|
465
|
-
|
466
|
-
operation :show do
|
467
|
-
description 'Show an instance identified by "id" parameter.'
|
468
|
-
with_capability :instance
|
469
|
-
param :id, :string, :required
|
470
|
-
control { show(:instance) }
|
471
|
-
end
|
472
|
-
|
473
|
-
operation :create do
|
474
|
-
description "Create a new instance."
|
475
|
-
with_capability :create_instance
|
476
|
-
param :image_id, :string, :required
|
477
|
-
param :realm_id, :string, :optional
|
478
|
-
param :hwp_id, :string, :optional
|
479
|
-
control do
|
480
|
-
@instance = driver.create_instance(credentials, params[:image_id], params)
|
481
|
-
if @instance.kind_of? Array
|
482
|
-
@elements = @instance
|
483
|
-
action_handler = "index"
|
484
|
-
else
|
485
|
-
response['Location'] = instance_url(@instance.id)
|
486
|
-
action_handler = "show"
|
487
|
-
end
|
488
|
-
status 201 # Created
|
489
|
-
respond_to do |format|
|
490
|
-
format.xml { haml :"instances/#{action_handler}" }
|
491
|
-
format.json do
|
492
|
-
if @elements
|
493
|
-
convert_to_json(:instances, @elements)
|
494
|
-
else
|
495
|
-
convert_to_json(:instance, @elements)
|
496
|
-
end
|
497
|
-
end
|
498
|
-
format.html do
|
499
|
-
if @elements
|
500
|
-
haml :"instances/index"
|
501
|
-
elsif @instance and @instance.id
|
502
|
-
response['Location'] = instance_url(@instance.id)
|
503
|
-
redirect instance_url(@instance.id)
|
504
|
-
else
|
505
|
-
redirect instances_url
|
506
|
-
end
|
507
|
-
end
|
508
|
-
end
|
509
|
-
end
|
510
|
-
end
|
511
|
-
|
512
|
-
operation :reboot, :method => :post, :member => true do
|
513
|
-
description "Reboot a running instance."
|
514
|
-
with_capability :reboot_instance
|
515
|
-
param :id, :string, :required
|
516
|
-
control { instance_action(:reboot) }
|
517
|
-
end
|
518
|
-
|
519
|
-
operation :start, :method => :post, :member => true do
|
520
|
-
description "Start an instance."
|
521
|
-
with_capability :start_instance
|
522
|
-
param :id, :string, :required
|
523
|
-
control { instance_action(:start) }
|
524
|
-
end
|
525
|
-
|
526
|
-
operation :stop, :method => :post, :member => true do
|
527
|
-
description "Stop a running instance."
|
528
|
-
with_capability :stop_instance
|
529
|
-
param :id, :string, :required
|
530
|
-
control { instance_action(:stop) }
|
531
|
-
end
|
532
|
-
|
533
|
-
operation :destroy do
|
534
|
-
description "Destroy an instance."
|
535
|
-
with_capability :destroy_instance
|
536
|
-
param :id, :string, :required
|
537
|
-
control { instance_action(:destroy) }
|
538
|
-
end
|
539
|
-
|
540
|
-
operation :run, :method => :post, :member => true do
|
541
|
-
description <<END
|
542
|
-
Run command on instance. Either password or private key must be send
|
543
|
-
in order to execute command. Authetication method should be advertised
|
544
|
-
in instance.
|
545
|
-
END
|
546
|
-
with_capability :run_on_instance
|
547
|
-
param :id, :string, :required
|
548
|
-
param :cmd, :string, :required, [], "Shell command to run on instance"
|
549
|
-
param :private_key, :string, :optional, [], "Private key in PEM format for authentication"
|
550
|
-
param :password, :string, :optional, [], "Password used for authentication"
|
551
|
-
control do
|
552
|
-
@output = driver.run_on_instance(credentials, params)
|
553
|
-
respond_to do |format|
|
554
|
-
format.xml { haml :"instances/run" }
|
555
|
-
format.html { haml :"instances/run" }
|
556
|
-
end
|
557
|
-
end
|
558
|
-
end
|
559
|
-
end
|
560
|
-
|
561
|
-
collection :hardware_profiles do
|
562
|
-
description <<END
|
563
|
-
A hardware profile represents a configuration of resources upon which a
|
564
|
-
machine may be deployed. It defines aspects such as local disk storage,
|
565
|
-
available RAM, and architecture. Each provider is free to define as many
|
566
|
-
(or as few) hardware profiles as desired.
|
567
|
-
END
|
568
|
-
|
569
|
-
operation :index do
|
570
|
-
description "List of available hardware profiles."
|
571
|
-
with_capability :hardware_profiles
|
572
|
-
param :id, :string
|
573
|
-
param :architecture, :string, :optional, [ 'i386', 'x86_64' ]
|
574
|
-
control do
|
575
|
-
@profiles = driver.hardware_profiles(credentials, params)
|
576
|
-
respond_to do |format|
|
577
|
-
format.xml { haml :'hardware_profiles/index' }
|
578
|
-
format.html { haml :'hardware_profiles/index' }
|
579
|
-
format.json { convert_to_json(:hardware_profile, @profiles) }
|
580
|
-
end
|
581
|
-
end
|
582
|
-
end
|
583
|
-
|
584
|
-
operation :show do
|
585
|
-
description "Show specific hardware profile."
|
586
|
-
with_capability :hardware_profile
|
587
|
-
param :id, :string, :required
|
588
|
-
control do
|
589
|
-
@profile = driver.hardware_profile(credentials, params[:id])
|
590
|
-
if @profile
|
591
|
-
respond_to do |format|
|
592
|
-
format.xml { haml :'hardware_profiles/show', :layout => false }
|
593
|
-
format.html { haml :'hardware_profiles/show' }
|
594
|
-
format.json { convert_to_json(:hardware_profile, @profile) }
|
595
|
-
end
|
596
|
-
else
|
597
|
-
report_error(404)
|
598
|
-
end
|
599
|
-
end
|
600
|
-
end
|
601
|
-
|
602
|
-
end
|
603
|
-
|
604
|
-
collection :storage_snapshots do
|
605
|
-
description "Storage snapshots description here"
|
606
|
-
|
607
|
-
operation :new do
|
608
|
-
description "A form to create a new storage snapshot"
|
609
|
-
control do
|
610
|
-
respond_to do |format|
|
611
|
-
format.html { haml :"storage_snapshots/new" }
|
612
|
-
end
|
613
|
-
end
|
614
|
-
end
|
615
|
-
|
616
|
-
operation :index do
|
617
|
-
description "List of storage snapshots."
|
618
|
-
with_capability :storage_snapshots
|
619
|
-
param :id, :string
|
620
|
-
control { filter_all(:storage_snapshots) }
|
621
|
-
end
|
622
|
-
|
623
|
-
operation :show do
|
624
|
-
description "Show storage snapshot."
|
625
|
-
with_capability :storage_snapshot
|
626
|
-
param :id, :string, :required
|
627
|
-
control { show(:storage_snapshot) }
|
628
|
-
end
|
629
|
-
|
630
|
-
operation :create do
|
631
|
-
description "Create a new snapshot from volume"
|
632
|
-
with_capability :create_storage_snapshot
|
633
|
-
param :volume_id, :string, :required
|
634
|
-
control do
|
635
|
-
@storage_snapshot = driver.create_storage_snapshot(credentials, params)
|
636
|
-
status 201 # Created
|
637
|
-
response['Location'] = storage_snapshot_url(@storage_snapshot.id)
|
638
|
-
show(:storage_snapshot)
|
639
|
-
end
|
640
|
-
end
|
641
|
-
|
642
|
-
operation :destroy do
|
643
|
-
description "Delete storage snapshot"
|
644
|
-
with_capability :destroy_storage_snapshot
|
645
|
-
param :id, :string, :required
|
646
|
-
control do
|
647
|
-
driver.destroy_storage_snapshot(credentials, params)
|
648
|
-
status 204
|
649
|
-
respond_to do |format|
|
650
|
-
format.xml
|
651
|
-
format.json
|
652
|
-
format.html { redirect(storage_snapshots_url) }
|
653
|
-
end
|
654
|
-
end
|
655
|
-
end
|
656
|
-
end
|
657
|
-
|
658
|
-
collection :storage_volumes do
|
659
|
-
description "Storage volumes description here"
|
660
|
-
|
661
|
-
operation :new do
|
662
|
-
description "A form to create a new storage volume"
|
663
|
-
control do
|
664
|
-
respond_to do |format|
|
665
|
-
format.html { haml :"storage_volumes/new" }
|
666
|
-
end
|
667
|
-
end
|
668
|
-
end
|
21
|
+
require 'sinatra/base'
|
22
|
+
require 'sinatra/rabbit'
|
669
23
|
|
670
|
-
|
671
|
-
|
672
|
-
|
673
|
-
|
674
|
-
|
675
|
-
end
|
24
|
+
require_relative '../sinatra'
|
25
|
+
require_relative './models'
|
26
|
+
require_relative './drivers'
|
27
|
+
require_relative './helpers'
|
28
|
+
require_relative './collections'
|
676
29
|
|
677
|
-
|
678
|
-
|
679
|
-
with_capability :storage_volume
|
680
|
-
param :id, :string, :required
|
681
|
-
control { show(:storage_volume) }
|
682
|
-
end
|
30
|
+
module Deltacloud
|
31
|
+
class API < Collections::Base
|
683
32
|
|
684
|
-
|
685
|
-
|
686
|
-
|
687
|
-
|
688
|
-
|
689
|
-
|
690
|
-
|
691
|
-
|
692
|
-
status 201
|
693
|
-
response['Location'] = storage_volume_url(@storage_volume.id)
|
694
|
-
respond_to do |format|
|
695
|
-
format.xml { haml :"storage_volumes/show" }
|
696
|
-
format.html { haml :"storage_volumes/show" }
|
697
|
-
format.json { convert_to_json(:storage_volume, @storage_volume) }
|
698
|
-
end
|
699
|
-
end
|
700
|
-
end
|
701
|
-
|
702
|
-
operation :attach_instance, :method=>:get, :member=>true do
|
703
|
-
description "A form to attach a storage volume to an instance"
|
704
|
-
control do
|
705
|
-
@instances = driver.instances(credentials)
|
706
|
-
respond_to do |format|
|
707
|
-
format.html{ haml :"storage_volumes/attach"}
|
708
|
-
end
|
709
|
-
end
|
710
|
-
end
|
33
|
+
# Enable logging
|
34
|
+
use Rack::CommonLogger
|
35
|
+
use Rack::Date
|
36
|
+
use Rack::ETag
|
37
|
+
use Rack::MatrixParams
|
38
|
+
use Rack::DriverSelect
|
39
|
+
use Rack::Accept
|
40
|
+
use Rack::MediaType
|
711
41
|
|
712
|
-
|
713
|
-
|
714
|
-
with_capability :attach_storage_volume
|
715
|
-
param :id, :string, :required
|
716
|
-
param :instance_id,:string, :required
|
717
|
-
param :device, :string, :required
|
718
|
-
control do
|
719
|
-
@storage_volume = driver.attach_storage_volume(credentials, params)
|
720
|
-
status 202
|
721
|
-
respond_to do |format|
|
722
|
-
format.html { redirect(storage_volume_url(params[:id]))}
|
723
|
-
format.xml { haml :"storage_volumes/show" }
|
724
|
-
format.json { convert_to_json(:storage_volume, @storage_volume) }
|
725
|
-
end
|
726
|
-
end
|
727
|
-
end
|
42
|
+
include Deltacloud::Helpers
|
43
|
+
include Deltacloud::Collections
|
728
44
|
|
729
|
-
|
730
|
-
description "Detach storage volume to instance"
|
731
|
-
with_capability :detach_storage_volume
|
732
|
-
param :id, :string, :required
|
733
|
-
control do
|
734
|
-
volume = driver.storage_volume(credentials, :id => params[:id])
|
735
|
-
@storage_volume = driver.detach_storage_volume(credentials, :id => volume.id, :instance_id => volume.instance_id, :device => volume.device)
|
736
|
-
status 202
|
737
|
-
respond_to do |format|
|
738
|
-
format.html { redirect(storage_volume_url(params[:id]))}
|
739
|
-
format.xml { haml :"storage_volumes/show" }
|
740
|
-
format.json { convert_to_json(:storage_volume, @storage_volume) }
|
741
|
-
end
|
742
|
-
end
|
743
|
-
end
|
45
|
+
set :config, Deltacloud[:deltacloud]
|
744
46
|
|
745
|
-
|
746
|
-
|
747
|
-
|
748
|
-
param :id, :string, :optional
|
749
|
-
control do
|
750
|
-
driver.destroy_storage_volume(credentials, params)
|
751
|
-
status 204
|
752
|
-
respond_to do |format|
|
753
|
-
format.xml
|
754
|
-
format.json
|
755
|
-
format.html { redirect(storage_volumes_url) }
|
47
|
+
get Deltacloud.config[:deltacloud].root_url + '/?' do
|
48
|
+
if params[:force_auth]
|
49
|
+
return [401, 'Authentication failed'] unless driver.valid_credentials?(credentials)
|
756
50
|
end
|
757
|
-
end
|
758
|
-
end
|
759
|
-
|
760
|
-
end
|
761
|
-
|
762
|
-
collection :keys do
|
763
|
-
description "Instance authentication credentials."
|
764
|
-
|
765
|
-
operation :new do
|
766
|
-
description "A form to create a new key resource"
|
767
|
-
control do
|
768
51
|
respond_to do |format|
|
769
|
-
format.
|
770
|
-
|
771
|
-
|
772
|
-
end
|
773
|
-
|
774
|
-
operation :index do
|
775
|
-
description "List all available credentials which could be used for instance authentication."
|
776
|
-
with_capability :keys
|
777
|
-
control do
|
778
|
-
filter_all :keys
|
779
|
-
end
|
780
|
-
end
|
781
|
-
|
782
|
-
operation :show do
|
783
|
-
description "Show details about given instance credential."
|
784
|
-
with_capability :key
|
785
|
-
param :id, :string, :required
|
786
|
-
control { show :key }
|
787
|
-
end
|
788
|
-
|
789
|
-
operation :create do
|
790
|
-
description "Create a new instance credential if backend supports this."
|
791
|
-
with_capability :create_key
|
792
|
-
param :name, :string, :required
|
793
|
-
control do
|
794
|
-
@key = driver.create_key(credentials, { :key_name => params[:name] })
|
795
|
-
status 201
|
796
|
-
response['Location'] = key_url(@key.id)
|
797
|
-
respond_to do |format|
|
798
|
-
format.xml { haml :"keys/show", :ugly => true }
|
799
|
-
format.html { haml :"keys/show" }
|
800
|
-
format.json { convert_to_json(:key, @key)}
|
801
|
-
end
|
802
|
-
end
|
803
|
-
end
|
804
|
-
|
805
|
-
operation :destroy do
|
806
|
-
description "Destroy given instance credential if backend supports this."
|
807
|
-
with_capability :destroy_key
|
808
|
-
param :id, :string, :required
|
809
|
-
control do
|
810
|
-
driver.destroy_key(credentials, { :id => params[:id]})
|
811
|
-
status 204
|
812
|
-
respond_to do |format|
|
813
|
-
format.xml
|
814
|
-
format.json
|
815
|
-
format.html { redirect(keys_url) }
|
816
|
-
end
|
817
|
-
end
|
818
|
-
end
|
819
|
-
|
820
|
-
end
|
821
|
-
|
822
|
-
#get html form for creating a new blob
|
823
|
-
|
824
|
-
# The URL for getting the new blob form for the HTML UI looks like the URL
|
825
|
-
# for getting the details of an existing blob. To make collisions less
|
826
|
-
# likely, we use a name for the form that will rarely be the name of an
|
827
|
-
# existing blob
|
828
|
-
NEW_BLOB_FORM_ID = "new_blob_form_d15cfd90"
|
829
|
-
|
830
|
-
get "#{settings.root_url}/buckets/:bucket/#{NEW_BLOB_FORM_ID}" do
|
831
|
-
@bucket_id = params[:bucket]
|
832
|
-
respond_to do |format|
|
833
|
-
format.html {haml :"blobs/new"}
|
834
|
-
end
|
835
|
-
end
|
836
|
-
|
837
|
-
collection :buckets do
|
838
|
-
description "Cloud Storage buckets - aka buckets|directories|folders"
|
839
|
-
|
840
|
-
collection :blobs do
|
841
|
-
description "Blobs associated with given bucket"
|
842
|
-
|
843
|
-
operation :show do
|
844
|
-
description "Display blob"
|
845
|
-
control do
|
846
|
-
@blob = driver.blob(credentials, { :id => params[:blob], 'bucket' => params[:bucket]})
|
847
|
-
if @blob
|
848
|
-
respond_to do |format|
|
849
|
-
format.xml { haml :"blobs/show" }
|
850
|
-
format.html { haml :"blobs/show" }
|
851
|
-
format.json { convert_to_json(:blob, @blob) }
|
852
|
-
end
|
853
|
-
else
|
854
|
-
report_error(404)
|
855
|
-
end
|
856
|
-
end
|
857
|
-
|
858
|
-
end
|
859
|
-
|
860
|
-
operation :create do
|
861
|
-
description "Create new blob"
|
862
|
-
control do
|
863
|
-
bucket_id = params[:bucket]
|
864
|
-
blob_id = params['blob_id']
|
865
|
-
blob_data = params['blob_data']
|
866
|
-
user_meta = {}
|
867
|
-
#metadata from params (i.e., passed by http form post, e.g. browser)
|
868
|
-
max = params[:meta_params]
|
869
|
-
if(max)
|
870
|
-
(1..max.to_i).each do |i|
|
871
|
-
key = params[:"meta_name#{i}"]
|
872
|
-
key = "HTTP_X_Deltacloud_Blobmeta_#{key}"
|
873
|
-
value = params[:"meta_value#{i}"]
|
874
|
-
user_meta[key] = value
|
875
|
-
end
|
876
|
-
end
|
877
|
-
@blob = driver.create_blob(credentials, bucket_id, blob_id, blob_data, user_meta)
|
878
|
-
respond_to do |format|
|
879
|
-
format.xml { haml :"blobs/show" }
|
880
|
-
format.html { haml :"blobs/show"}
|
881
|
-
end
|
882
|
-
end
|
883
|
-
end
|
884
|
-
|
885
|
-
operation :destroy do
|
886
|
-
description "Destroy given blob"
|
887
|
-
control do
|
888
|
-
bucket_id = params[:bucket]
|
889
|
-
blob_id = params[:blob]
|
890
|
-
driver.delete_blob(credentials, bucket_id, blob_id)
|
891
|
-
status 204
|
892
|
-
respond_to do |format|
|
893
|
-
format.xml
|
894
|
-
format.json
|
895
|
-
format.html { redirect(bucket_url(bucket_id)) }
|
896
|
-
end
|
897
|
-
end
|
898
|
-
end
|
899
|
-
|
900
|
-
operation :stream, :member => true, :standard => true, :method => :put do
|
901
|
-
description "Stream new blob data into the blob"
|
902
|
-
control do
|
903
|
-
if(env["BLOB_SUCCESS"]) #ie got a 200ok after putting blob
|
904
|
-
content_type = env["CONTENT_TYPE"]
|
905
|
-
content_type ||= ""
|
906
|
-
@blob = driver.blob(credentials, {:id => params[:blob],
|
907
|
-
'bucket' => params[:bucket]})
|
908
|
-
respond_to do |format|
|
909
|
-
format.xml { haml :"blobs/show" }
|
910
|
-
format.html { haml :"blobs/show" }
|
911
|
-
format.json { convert_to_json(:blob, @blob) }
|
912
|
-
end
|
913
|
-
elsif(env["BLOB_FAIL"])
|
914
|
-
report_error(500) #OK?
|
915
|
-
else # small blobs - < 112kb dont hit the streaming monkey patch - use 'normal' create_blob
|
916
|
-
# also, if running under webrick don't hit the streaming patch (Thin specific)
|
917
|
-
bucket_id = params[:bucket]
|
918
|
-
blob_id = params[:blob]
|
919
|
-
temp_file = Tempfile.new("temp_blob_file")
|
920
|
-
temp_file.write(env['rack.input'].read)
|
921
|
-
temp_file.flush
|
922
|
-
content_type = env['CONTENT_TYPE'] || ""
|
923
|
-
blob_data = {:tempfile => temp_file, :type => content_type}
|
924
|
-
user_meta = BlobHelper::extract_blob_metadata_hash(request.env)
|
925
|
-
@blob = driver.create_blob(credentials, bucket_id, blob_id, blob_data, user_meta)
|
926
|
-
temp_file.delete
|
927
|
-
respond_to do |format|
|
928
|
-
format.xml { haml :"blobs/show" }
|
929
|
-
format.html { haml :"blobs/show"}
|
930
|
-
end
|
931
|
-
end
|
932
|
-
end
|
933
|
-
end
|
934
|
-
|
935
|
-
operation :metadata, :member => true, :standard => true, :method => :head do
|
936
|
-
description "Get blob metadata"
|
937
|
-
control do
|
938
|
-
@blob_id = params[:blob]
|
939
|
-
@blob_metadata = driver.blob_metadata(credentials, {:id => params[:blob], 'bucket' => params[:bucket]})
|
940
|
-
if @blob_metadata
|
941
|
-
@blob_metadata.each do |k,v|
|
942
|
-
headers["X-Deltacloud-Blobmeta-#{k}"] = v
|
943
|
-
end
|
944
|
-
status 204
|
945
|
-
respond_to do |format|
|
946
|
-
format.xml
|
947
|
-
format.json
|
948
|
-
end
|
949
|
-
else
|
950
|
-
report_error(404)
|
951
|
-
end
|
952
|
-
end
|
953
|
-
end
|
954
|
-
|
955
|
-
operation :update, :member => true, :method => :post do
|
956
|
-
description "Update blob metadata"
|
957
|
-
control do
|
958
|
-
meta_hash = BlobHelper::extract_blob_metadata_hash(request.env)
|
959
|
-
success = driver.update_blob_metadata(credentials, {'bucket'=>params[:bucket], :id =>params[:blob], 'meta_hash' => meta_hash})
|
960
|
-
if(success)
|
961
|
-
meta_hash.each do |k,v|
|
962
|
-
headers["X-Deltacloud-Blobmeta-#{k}"] = v
|
963
|
-
end
|
964
|
-
status 204
|
965
|
-
respond_to do |format|
|
966
|
-
format.xml
|
967
|
-
format.json
|
968
|
-
end
|
969
|
-
else
|
970
|
-
report_error(404) #FIXME is this the right error code?
|
971
|
-
end
|
52
|
+
format.xml { haml :"api/show" }
|
53
|
+
format.json { xml_to_json :"api/show" }
|
54
|
+
format.html { haml :"api/show" }
|
972
55
|
end
|
973
56
|
end
|
974
57
|
|
975
|
-
|
976
|
-
|
977
|
-
|
978
|
-
|
979
|
-
|
980
|
-
|
981
|
-
|
982
|
-
|
983
|
-
|
58
|
+
post Deltacloud.config[:deltacloud].root_url + '/?' do
|
59
|
+
param_driver, param_provider = params["driver"], params["provider"]
|
60
|
+
if param_driver
|
61
|
+
redirect "#{Deltacloud.config[:deltacloud].root_url}\;driver=#{param_driver}", 301
|
62
|
+
elsif param_provider && param_provider != "default"
|
63
|
+
#FIXME NEEDS A BETTER WAY OF GRABBING CURRENT DRIVER FROM MATRIX PARAMS...
|
64
|
+
current_matrix_driver = env["HTTP_REFERER"].match(/\;(driver)=(\w*).*$/i)
|
65
|
+
if current_matrix_driver
|
66
|
+
redirect "#{Deltacloud.config[:deltacloud].root_url}\;driver=#{$2}\;provider=#{param_provider}", 301
|
984
67
|
else
|
985
|
-
|
68
|
+
redirect "#{Deltacloud.config[:deltacloud].root_url}\;provider=#{param_provider}", 301
|
986
69
|
end
|
70
|
+
else
|
71
|
+
redirect "#{Deltacloud.config[:deltacloud].root_url}", 301
|
987
72
|
end
|
988
73
|
end
|
989
74
|
|
990
75
|
end
|
991
|
-
|
992
|
-
operation :new do
|
993
|
-
description "A form to create a new bucket resource"
|
994
|
-
control do
|
995
|
-
respond_to do |format|
|
996
|
-
format.html { haml :"buckets/new" }
|
997
|
-
end
|
998
|
-
end
|
999
|
-
end
|
1000
|
-
|
1001
|
-
operation :index do
|
1002
|
-
description "List buckets associated with this account"
|
1003
|
-
with_capability :buckets
|
1004
|
-
param :id, :string
|
1005
|
-
param :name, :string
|
1006
|
-
param :size, :string
|
1007
|
-
control { filter_all(:buckets) }
|
1008
|
-
end
|
1009
|
-
|
1010
|
-
operation :show do
|
1011
|
-
description "Show bucket"
|
1012
|
-
with_capability :bucket
|
1013
|
-
param :id, :string
|
1014
|
-
control { show(:bucket) }
|
1015
|
-
end
|
1016
|
-
|
1017
|
-
operation :create do
|
1018
|
-
description "Create a new bucket (POST /api/buckets)"
|
1019
|
-
with_capability :create_bucket
|
1020
|
-
param :name, :string, :required
|
1021
|
-
control do
|
1022
|
-
@bucket = driver.create_bucket(credentials, params[:name], params)
|
1023
|
-
status 201
|
1024
|
-
response['Location'] = bucket_url(@bucket.id)
|
1025
|
-
respond_to do |format|
|
1026
|
-
format.xml { haml :"buckets/show" }
|
1027
|
-
format.json { convert_to_json(:bucket, @bucket) }
|
1028
|
-
format.html do
|
1029
|
-
redirect bucket_url(@bucket.id) if @bucket and @bucket.id
|
1030
|
-
redirect buckets_url
|
1031
|
-
end
|
1032
|
-
end
|
1033
|
-
end
|
1034
|
-
end
|
1035
|
-
|
1036
|
-
operation :destroy do
|
1037
|
-
description "Delete a bucket by name - bucket must be empty"
|
1038
|
-
with_capability :delete_bucket
|
1039
|
-
param :id, :string, :required
|
1040
|
-
control do
|
1041
|
-
driver.delete_bucket(credentials, params[:id], params)
|
1042
|
-
status 204
|
1043
|
-
respond_to do |format|
|
1044
|
-
format.xml
|
1045
|
-
format.json
|
1046
|
-
format.html { redirect(buckets_url) }
|
1047
|
-
end
|
1048
|
-
end
|
1049
|
-
end
|
1050
|
-
|
1051
|
-
end
|
1052
|
-
|
1053
|
-
get "#{settings.root_url}/addresses/:id/associate" do
|
1054
|
-
@instances = driver.instances(credentials)
|
1055
|
-
@address = Address::new(:id => params[:id])
|
1056
|
-
respond_to do |format|
|
1057
|
-
format.html { haml :"addresses/associate" }
|
1058
|
-
end
|
1059
|
-
end
|
1060
|
-
|
1061
|
-
collection :addresses do
|
1062
|
-
description "Manage IP addresses"
|
1063
|
-
|
1064
|
-
operation :index do
|
1065
|
-
description "List IP addresses assigned to your account."
|
1066
|
-
with_capability :addresses
|
1067
|
-
control do
|
1068
|
-
filter_all :addresses
|
1069
|
-
end
|
1070
|
-
end
|
1071
|
-
|
1072
|
-
operation :show do
|
1073
|
-
description "Show details about IP addresses specified by given ID"
|
1074
|
-
with_capability :address
|
1075
|
-
param :id, :string, :required
|
1076
|
-
control { show :address }
|
1077
|
-
end
|
1078
|
-
|
1079
|
-
operation :create do
|
1080
|
-
description "Acquire a new IP address for use with your account."
|
1081
|
-
with_capability :create_address
|
1082
|
-
control do
|
1083
|
-
@address = driver.create_address(credentials, {})
|
1084
|
-
status 201 # Created
|
1085
|
-
response['Location'] = address_url(@address.id)
|
1086
|
-
respond_to do |format|
|
1087
|
-
format.xml { haml :"addresses/show", :ugly => true }
|
1088
|
-
format.html { haml :"addresses/_address", :layout => false }
|
1089
|
-
format.json { convert_to_json(:address, @address) }
|
1090
|
-
end
|
1091
|
-
end
|
1092
|
-
end
|
1093
|
-
|
1094
|
-
operation :destroy do
|
1095
|
-
description "Release an IP address associated with your account"
|
1096
|
-
with_capability :destroy_address
|
1097
|
-
param :id, :string, :required
|
1098
|
-
control do
|
1099
|
-
driver.destroy_address(credentials, { :id => params[:id]})
|
1100
|
-
status 204
|
1101
|
-
respond_to do |format|
|
1102
|
-
format.xml
|
1103
|
-
format.json
|
1104
|
-
format.html { redirect(addresses_url) }
|
1105
|
-
end
|
1106
|
-
end
|
1107
|
-
end
|
1108
|
-
|
1109
|
-
operation :associate, :method => :post, :member => true do
|
1110
|
-
description "Associate an IP address to an instance"
|
1111
|
-
with_capability :associate_address
|
1112
|
-
param :id, :string, :required
|
1113
|
-
param :instance_id, :string, :required
|
1114
|
-
control do
|
1115
|
-
driver.associate_address(credentials, { :id => params[:id], :instance_id => params[:instance_id]})
|
1116
|
-
status 202 # Accepted
|
1117
|
-
respond_to do |format|
|
1118
|
-
format.xml
|
1119
|
-
format.json
|
1120
|
-
format.html { redirect(address_url(params[:id])) }
|
1121
|
-
end
|
1122
|
-
end
|
1123
|
-
end
|
1124
|
-
|
1125
|
-
operation :disassociate, :method => :post, :member => true do
|
1126
|
-
description "Disassociate an IP address from an instance"
|
1127
|
-
with_capability :associate_address
|
1128
|
-
param :id, :string, :required
|
1129
|
-
control do
|
1130
|
-
driver.disassociate_address(credentials, { :id => params[:id] })
|
1131
|
-
status 202 # Accepted
|
1132
|
-
respond_to do |format|
|
1133
|
-
format.xml
|
1134
|
-
format.json
|
1135
|
-
format.html { redirect(address_url(params[:id])) }
|
1136
|
-
end
|
1137
|
-
end
|
1138
|
-
end
|
1139
|
-
|
1140
|
-
end
|
1141
|
-
|
1142
|
-
#delete a firewall rule
|
1143
|
-
delete '/api/firewalls/:firewall/:rule' do
|
1144
|
-
opts = {}
|
1145
|
-
opts[:firewall] = params[:firewall]
|
1146
|
-
opts[:rule_id] = params[:rule]
|
1147
|
-
driver.delete_firewall_rule(credentials, opts)
|
1148
|
-
status 204
|
1149
|
-
respond_to do |format|
|
1150
|
-
format.xml
|
1151
|
-
format.json
|
1152
|
-
format.html {redirect firewall_url(params[:firewall])}
|
1153
|
-
end
|
1154
76
|
end
|
1155
77
|
|
1156
|
-
#FIREWALLS
|
1157
|
-
collection :firewalls do
|
1158
|
-
description "Allow user to define firewall rules for an instance (ec2 security groups) eg expose ssh access [port 22, tcp]."
|
1159
|
-
|
1160
|
-
operation :new do
|
1161
|
-
description "A form to create a new firewall resource"
|
1162
|
-
control do
|
1163
|
-
respond_to do |format|
|
1164
|
-
format.html { haml :"firewalls/new" }
|
1165
|
-
end
|
1166
|
-
end
|
1167
|
-
end
|
1168
|
-
|
1169
|
-
operation :new_rule, :form => true, :member => true, :method => :get do
|
1170
|
-
description "A form to create a new firewall rule"
|
1171
|
-
param :id, :string, :required
|
1172
|
-
control do
|
1173
|
-
@firewall_name = params[:id]
|
1174
|
-
respond_to do |format|
|
1175
|
-
format.html {haml :"firewalls/new_rule" }
|
1176
|
-
end
|
1177
|
-
end
|
1178
|
-
end
|
1179
|
-
|
1180
|
-
operation :index do
|
1181
|
-
description 'List all firewalls'
|
1182
|
-
with_capability :firewalls
|
1183
|
-
control { filter_all(:firewalls) }
|
1184
|
-
end
|
1185
|
-
|
1186
|
-
operation :show do
|
1187
|
-
description 'Show details for a specific firewall - list all rules'
|
1188
|
-
with_capability :firewall
|
1189
|
-
param :id, :string, :required
|
1190
|
-
control { show(:firewall) }
|
1191
|
-
end
|
1192
|
-
|
1193
|
-
operation :create do
|
1194
|
-
description 'Create a new firewall'
|
1195
|
-
with_capability :create_firewall
|
1196
|
-
param :name, :string, :required
|
1197
|
-
param :description, :string, :required
|
1198
|
-
control do
|
1199
|
-
@firewall = driver.create_firewall(credentials, params )
|
1200
|
-
status 201 # Created
|
1201
|
-
response['Location'] = firewall_url(@firewall.id)
|
1202
|
-
respond_to do |format|
|
1203
|
-
format.xml { haml :"firewalls/show" }
|
1204
|
-
format.html { haml :"firewalls/show" }
|
1205
|
-
format.json { convert_to_json(:firewall, @firewall) }
|
1206
|
-
end
|
1207
|
-
end
|
1208
|
-
end
|
1209
|
-
|
1210
|
-
operation :destroy do
|
1211
|
-
description 'Delete a specified firewall - error if firewall has rules'
|
1212
|
-
with_capability :delete_firewall
|
1213
|
-
param :id, :string, :required
|
1214
|
-
control do
|
1215
|
-
driver.delete_firewall(credentials, params)
|
1216
|
-
status 204
|
1217
|
-
respond_to do |format|
|
1218
|
-
format.xml
|
1219
|
-
format.json
|
1220
|
-
format.html { redirect(firewalls_url) }
|
1221
|
-
end
|
1222
|
-
end
|
1223
|
-
end
|
1224
|
-
|
1225
|
-
#create a new firewall rule - POST /api/firewalls/:firewall/rules
|
1226
|
-
operation :rules, :method => :post, :member => true do
|
1227
|
-
description 'Create a new firewall rule for the specified firewall'
|
1228
|
-
param :id, :required, :string, [], "Name of firewall in which to apply this rule"
|
1229
|
-
param :protocol, :required, :string, ['tcp','udp','icmp'], "Transport layer protocol for the rule"
|
1230
|
-
param :port_from, :required, :string, [], "Start of port range for the rule"
|
1231
|
-
param :port_to, :required, :string, [], "End of port range for the rule"
|
1232
|
-
with_capability :create_firewall_rule
|
1233
|
-
control do
|
1234
|
-
#source IPs from params
|
1235
|
-
addresses = params.inject([]){|result,current| result << current.last unless current.grep(/^ip[-_]address/i).empty?; result}
|
1236
|
-
#source groups from params
|
1237
|
-
groups = {}
|
1238
|
-
max_groups = params.select{|k,v| k=~/^group/}.size/2
|
1239
|
-
for i in (1..max_groups) do
|
1240
|
-
groups.merge!({params["group#{i}"]=>params["group#{i}owner"]})
|
1241
|
-
end
|
1242
|
-
params['addresses'] = addresses
|
1243
|
-
params['groups'] = groups
|
1244
|
-
if addresses.empty? && groups.empty?
|
1245
|
-
raise Deltacloud::Validation::Failure.new(nil, "No sources. Specify at least one source ip_address or group")
|
1246
|
-
end
|
1247
|
-
driver.create_firewall_rule(credentials, params)
|
1248
|
-
@firewall = driver.firewall(credentials, {:id => params[:id]})
|
1249
|
-
status 201
|
1250
|
-
respond_to do |format|
|
1251
|
-
format.xml { haml :"firewalls/show" }
|
1252
|
-
format.html { haml :"firewalls/show" }
|
1253
|
-
format.json { convert_to_json(:firewall, @firewall) }
|
1254
|
-
end
|
1255
|
-
end
|
1256
|
-
end
|
1257
|
-
|
1258
|
-
end
|