bosh-director 1.3160.0 → 1.3163.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/bin/bosh-director-worker +2 -14
- data/db/migrations/director/20150513225143_ip_addresses.rb +11 -0
- data/db/migrations/director/20150702004608_add_links.rb +8 -0
- data/db/migrations/director/20150708231924_add_link_spec.rb +7 -0
- data/db/migrations/director/20150724183256_add_debugging_to_ip_addresses.rb +8 -0
- data/db/migrations/director/20150730225029_add_uuid_to_instances.rb +16 -0
- data/db/migrations/director/20150803215805_add_availabililty_zone_and_cloud_properties_to_instances.rb +8 -0
- data/db/migrations/director/20150804211419_add_compilation_flag_to_instance.rb +7 -0
- data/db/migrations/director/20150918003455_add_bootstrap_node_to_instance.rb +7 -0
- data/db/migrations/director/20151008232214_add_dns_records.rb +7 -0
- data/db/migrations/director/20151015172551_add_orphan_disks_and_snapshots.rb +29 -0
- data/db/migrations/director/20151030222853_add_templates_to_instance.rb +10 -0
- data/db/migrations/director/20151031001039_add_spec_to_instance.rb +19 -0
- data/db/migrations/director/20151109190602_rename_orphan_columns.rb +13 -0
- data/lib/bosh/director.rb +19 -9
- data/lib/bosh/director/agent_client.rb +0 -17
- data/lib/bosh/director/api/cloud_config_manager.rb +7 -5
- data/lib/bosh/director/api/controllers/base_controller.rb +3 -2
- data/lib/bosh/director/api/controllers/cleanup_controller.rb +15 -0
- data/lib/bosh/director/api/controllers/deployments_controller.rb +38 -26
- data/lib/bosh/director/api/controllers/disks_controller.rb +20 -0
- data/lib/bosh/director/api/controllers/info_controller.rb +2 -2
- data/lib/bosh/director/api/controllers/releases_controller.rb +1 -16
- data/lib/bosh/director/api/controllers/stemcells_controller.rb +1 -9
- data/lib/bosh/director/api/deployment_manager.rb +2 -1
- data/lib/bosh/director/api/instance_lookup.rb +17 -0
- data/lib/bosh/director/api/instance_manager.rb +20 -10
- data/lib/bosh/director/api/release_manager.rb +28 -8
- data/lib/bosh/director/api/resurrector_manager.rb +9 -2
- data/lib/bosh/director/api/route_configuration.rb +2 -0
- data/lib/bosh/director/api/snapshot_manager.rb +9 -5
- data/lib/bosh/director/api/stemcell_manager.rb +50 -0
- data/lib/bosh/director/app.rb +1 -1
- data/lib/bosh/director/cloudcheck_helper.rb +119 -132
- data/lib/bosh/director/compile_task.rb +1 -1
- data/lib/bosh/director/compile_task_generator.rb +2 -2
- data/lib/bosh/director/config.rb +21 -12
- data/lib/bosh/director/deployment_deleter.rb +69 -0
- data/lib/bosh/director/deployment_plan.rb +35 -4
- data/lib/bosh/director/deployment_plan/agent_state_migrator.rb +47 -0
- data/lib/bosh/director/deployment_plan/assembler.rb +115 -241
- data/lib/bosh/director/deployment_plan/availability_zone.rb +27 -0
- data/lib/bosh/director/deployment_plan/cloud_manifest_parser.rb +144 -35
- data/lib/bosh/director/deployment_plan/compilation_config.rb +21 -19
- data/lib/bosh/director/deployment_plan/compilation_instance_pool.rb +169 -0
- data/lib/bosh/director/deployment_plan/deployment_repo.rb +4 -8
- data/lib/bosh/director/deployment_plan/deployment_spec_parser.rb +13 -1
- data/lib/bosh/director/deployment_plan/deployment_validator.rb +17 -0
- data/lib/bosh/director/deployment_plan/desired_instance.rb +15 -0
- data/lib/bosh/director/deployment_plan/{disk_pool.rb → disk_type.rb} +14 -19
- data/lib/bosh/director/deployment_plan/dynamic_network.rb +105 -53
- data/lib/bosh/director/deployment_plan/dynamic_network_subnet.rb +13 -0
- data/lib/bosh/director/deployment_plan/env.rb +18 -0
- data/lib/bosh/director/deployment_plan/global_network_resolver.rb +77 -0
- data/lib/bosh/director/deployment_plan/instance.rb +222 -390
- data/lib/bosh/director/deployment_plan/instance_network_reservations.rb +71 -0
- data/lib/bosh/director/deployment_plan/instance_plan.rb +336 -0
- data/lib/bosh/director/deployment_plan/instance_plan_factory.rb +54 -0
- data/lib/bosh/director/deployment_plan/instance_plan_sorter.rb +61 -0
- data/lib/bosh/director/deployment_plan/instance_planner.rb +101 -0
- data/lib/bosh/director/deployment_plan/instance_repository.rb +36 -0
- data/lib/bosh/director/deployment_plan/instance_spec.rb +154 -0
- data/lib/bosh/director/deployment_plan/ip_provider/database_ip_repo.rb +136 -0
- data/lib/bosh/director/deployment_plan/ip_provider/in_memory_ip_repo.rb +81 -0
- data/lib/bosh/director/deployment_plan/ip_provider/ip_provider.rb +153 -0
- data/lib/bosh/director/deployment_plan/ip_provider/ip_provider_factory.rb +22 -0
- data/lib/bosh/director/deployment_plan/job.rb +116 -53
- data/lib/bosh/director/deployment_plan/job_availability_zone_parser.rb +49 -0
- data/lib/bosh/director/deployment_plan/job_migrator.rb +90 -0
- data/lib/bosh/director/deployment_plan/job_network.rb +42 -0
- data/lib/bosh/director/deployment_plan/job_network_parser.rb +118 -0
- data/lib/bosh/director/deployment_plan/job_spec_parser.rb +123 -126
- data/lib/bosh/director/deployment_plan/links/link.rb +30 -0
- data/lib/bosh/director/deployment_plan/links/link_lookup.rb +66 -0
- data/lib/bosh/director/deployment_plan/links/link_path.rb +27 -0
- data/lib/bosh/director/deployment_plan/links/links_resolver.rb +70 -0
- data/lib/bosh/director/deployment_plan/links/template_link.rb +21 -0
- data/lib/bosh/director/deployment_plan/manifest_migrator.rb +3 -17
- data/lib/bosh/director/deployment_plan/manifest_validator.rb +46 -0
- data/lib/bosh/director/deployment_plan/manual_network.rb +70 -97
- data/lib/bosh/director/deployment_plan/manual_network_subnet.rb +148 -0
- data/lib/bosh/director/deployment_plan/network.rb +50 -39
- data/lib/bosh/director/deployment_plan/network_planner.rb +4 -0
- data/lib/bosh/director/deployment_plan/network_planner/plan.rb +26 -0
- data/lib/bosh/director/deployment_plan/network_planner/planner.rb +21 -0
- data/lib/bosh/director/deployment_plan/network_planner/reservation_reconciler.rb +81 -0
- data/lib/bosh/director/deployment_plan/network_planner/vip_static_ips_planner.rb +50 -0
- data/lib/bosh/director/deployment_plan/network_settings.rb +65 -0
- data/lib/bosh/director/deployment_plan/options/skip_drain.rb +7 -0
- data/lib/bosh/director/deployment_plan/package_validator.rb +79 -0
- data/lib/bosh/director/deployment_plan/placement_planner.rb +8 -0
- data/lib/bosh/director/deployment_plan/placement_planner/availability_zone_picker.rb +90 -0
- data/lib/bosh/director/deployment_plan/placement_planner/bruteforce_ip_allocation.rb +124 -0
- data/lib/bosh/director/deployment_plan/placement_planner/index_assigner.rb +32 -0
- data/lib/bosh/director/deployment_plan/placement_planner/networks_to_static_ips.rb +125 -0
- data/lib/bosh/director/deployment_plan/placement_planner/placed_desired_instances.rb +40 -0
- data/lib/bosh/director/deployment_plan/placement_planner/plan.rb +42 -0
- data/lib/bosh/director/deployment_plan/placement_planner/static_ips_availability_zone_picker.rb +237 -0
- data/lib/bosh/director/deployment_plan/placement_planner/unplaced_existing_instances.rb +53 -0
- data/lib/bosh/director/deployment_plan/planner.rb +186 -74
- data/lib/bosh/director/deployment_plan/planner_factory.rb +30 -147
- data/lib/bosh/director/deployment_plan/release_version.rb +3 -3
- data/lib/bosh/director/deployment_plan/resource_pool.rb +2 -174
- data/lib/bosh/director/deployment_plan/stemcell.rb +57 -14
- data/lib/bosh/director/deployment_plan/steps/package_compile_step.rb +28 -135
- data/lib/bosh/director/deployment_plan/steps/update_step.rb +23 -44
- data/lib/bosh/director/deployment_plan/template.rb +15 -4
- data/lib/bosh/director/deployment_plan/vip_network.rb +14 -42
- data/lib/bosh/director/deployment_plan/vm.rb +1 -99
- data/lib/bosh/director/deployment_plan/vm_type.rb +27 -0
- data/lib/bosh/director/disk_manager.rb +268 -0
- data/lib/bosh/director/dns/canonicalizer.rb +28 -0
- data/lib/bosh/director/dns/dns_manager.rb +163 -0
- data/lib/bosh/director/dns/local_dns_repo.rb +20 -0
- data/lib/bosh/director/dns/powerdns.rb +170 -0
- data/lib/bosh/director/errand/job_manager.rb +18 -29
- data/lib/bosh/director/error_ignorer.rb +16 -0
- data/lib/bosh/director/errors.rb +51 -20
- data/lib/bosh/director/event_log.rb +6 -0
- data/lib/bosh/director/instance_deleter.rb +53 -81
- data/lib/bosh/director/instance_reuser.rb +89 -0
- data/lib/bosh/director/instance_updater.rb +139 -281
- data/lib/bosh/director/instance_updater/preparer.rb +8 -5
- data/lib/bosh/director/instance_updater/state_applier.rb +21 -0
- data/lib/bosh/director/ip_util.rb +46 -26
- data/lib/bosh/director/job_renderer.rb +22 -10
- data/lib/bosh/director/job_runner.rb +1 -4
- data/lib/bosh/director/job_updater.rb +47 -35
- data/lib/bosh/director/job_updater_factory.rb +5 -4
- data/lib/bosh/director/jobs/base_job.rb +8 -0
- data/lib/bosh/director/jobs/cleanup_artifacts.rb +93 -0
- data/lib/bosh/director/jobs/delete_deployment.rb +10 -154
- data/lib/bosh/director/jobs/delete_deployment_snapshots.rb +1 -1
- data/lib/bosh/director/jobs/delete_orphan_disks.rb +44 -0
- data/lib/bosh/director/jobs/delete_release.rb +19 -196
- data/lib/bosh/director/jobs/delete_stemcell.rb +10 -76
- data/lib/bosh/director/jobs/export_release.rb +41 -121
- data/lib/bosh/director/jobs/fetch_logs.rb +0 -6
- data/lib/bosh/director/jobs/helpers.rb +10 -0
- data/lib/bosh/director/jobs/helpers/blob_deleter.rb +24 -0
- data/lib/bosh/director/jobs/helpers/compiled_package_deleter.rb +24 -0
- data/lib/bosh/director/jobs/helpers/name_version_release_deleter.rb +48 -0
- data/lib/bosh/director/jobs/helpers/package_deleter.rb +33 -0
- data/lib/bosh/director/jobs/helpers/release_deleter.rb +52 -0
- data/lib/bosh/director/jobs/helpers/release_version_deleter.rb +115 -0
- data/lib/bosh/director/jobs/helpers/releases_to_delete_picker.rb +31 -0
- data/lib/bosh/director/jobs/helpers/stemcell_deleter.rb +61 -0
- data/lib/bosh/director/jobs/helpers/stemcells_to_delete_picker.rb +30 -0
- data/lib/bosh/director/jobs/helpers/template_deleter.rb +20 -0
- data/lib/bosh/director/jobs/release/release_job.rb +18 -7
- data/lib/bosh/director/jobs/run_errand.rb +57 -36
- data/lib/bosh/director/jobs/scheduled_orphan_cleanup.rb +46 -0
- data/lib/bosh/director/jobs/ssh.rb +50 -17
- data/lib/bosh/director/jobs/update_deployment.rb +29 -11
- data/lib/bosh/director/jobs/update_release.rb +25 -4
- data/lib/bosh/director/jobs/vm_state.rb +23 -32
- data/lib/bosh/director/lock.rb +13 -8
- data/lib/bosh/director/logs_fetcher.rb +1 -1
- data/lib/bosh/director/models.rb +3 -0
- data/lib/bosh/director/models/compiled_package.rb +3 -3
- data/lib/bosh/director/models/deployment.rb +10 -0
- data/lib/bosh/director/models/instance.rb +77 -1
- data/lib/bosh/director/models/ip_address.rb +26 -0
- data/lib/bosh/director/models/orphan_disk.rb +23 -0
- data/lib/bosh/director/models/orphan_snapshot.rb +14 -0
- data/lib/bosh/director/models/template.rb +32 -9
- data/lib/bosh/director/models/vm.rb +5 -8
- data/lib/bosh/director/network_reservation.rb +69 -99
- data/lib/bosh/director/problem_handlers/inactive_disk.rb +5 -20
- data/lib/bosh/director/problem_handlers/missing_disk.rb +2 -13
- data/lib/bosh/director/problem_resolver.rb +2 -2
- data/lib/bosh/director/problem_scanner/vm_scan_stage.rb +2 -21
- data/lib/bosh/director/scheduler.rb +23 -6
- data/lib/bosh/director/{instance_updater/stopper.rb → stopper.rb} +24 -18
- data/lib/bosh/director/tagged_logger.rb +30 -0
- data/lib/bosh/director/transactor.rb +9 -0
- data/lib/bosh/director/version.rb +1 -1
- data/lib/bosh/director/vm_creator.rb +91 -19
- data/lib/bosh/director/vm_deleter.rb +25 -0
- data/lib/bosh/director/vm_recreator.rb +15 -0
- data/lib/cloud/dummy.rb +381 -94
- metadata +110 -30
- data/lib/bosh/director/deployment_plan/dns_binder.rb +0 -45
- data/lib/bosh/director/deployment_plan/instance_vm_binder.rb +0 -37
- data/lib/bosh/director/deployment_plan/network_subnet.rb +0 -166
- data/lib/bosh/director/deployment_plan/resource_pools.rb +0 -68
- data/lib/bosh/director/dns_helper.rb +0 -223
- data/lib/bosh/director/instance_updater/network_updater.rb +0 -110
- data/lib/bosh/director/instance_updater/vm_updater.rb +0 -189
- data/lib/bosh/director/problem_handlers/out_of_sync_vm.rb +0 -64
- data/lib/bosh/director/problem_handlers/unbound_instance_vm.rb +0 -85
- data/lib/bosh/director/resource_pool_updater.rb +0 -174
- data/lib/bosh/director/vm_data.rb +0 -63
- data/lib/bosh/director/vm_reuser.rb +0 -63
@@ -0,0 +1,148 @@
|
|
1
|
+
module Bosh::Director
|
2
|
+
module DeploymentPlan
|
3
|
+
class ManualNetworkSubnet
|
4
|
+
extend ValidationHelper
|
5
|
+
extend IpUtil
|
6
|
+
|
7
|
+
attr_reader :network_name, :range, :gateway, :dns, :cloud_properties,
|
8
|
+
:netmask, :availability_zone_names, :restricted_ips, :static_ips
|
9
|
+
|
10
|
+
def self.parse(network_name, subnet_spec, availability_zones, legacy_reserved_ranges)
|
11
|
+
@logger = Config.logger
|
12
|
+
|
13
|
+
@logger.debug("reserved ranges #{legacy_reserved_ranges.inspect}")
|
14
|
+
range_property = safe_property(subnet_spec, "range", :class => String)
|
15
|
+
range = NetAddr::CIDR.create(range_property)
|
16
|
+
|
17
|
+
if range.size <= 1
|
18
|
+
raise NetworkInvalidRange,
|
19
|
+
"Invalid network range `#{range_property}', " +
|
20
|
+
"should include at least 2 IPs"
|
21
|
+
end
|
22
|
+
|
23
|
+
netmask = range.wildcard_mask
|
24
|
+
network_id = range.network(:Objectify => true)
|
25
|
+
broadcast = range.broadcast(:Objectify => true)
|
26
|
+
|
27
|
+
ignore_missing_gateway = Bosh::Director::Config.ignore_missing_gateway
|
28
|
+
gateway_property = safe_property(subnet_spec, "gateway", class: String, optional: ignore_missing_gateway)
|
29
|
+
if gateway_property
|
30
|
+
gateway = NetAddr::CIDR.create(gateway_property)
|
31
|
+
unless gateway.size == 1
|
32
|
+
invalid_gateway(network_name, "must be a single IP")
|
33
|
+
end
|
34
|
+
unless range.contains?(gateway)
|
35
|
+
invalid_gateway(network_name, "must be inside the range")
|
36
|
+
end
|
37
|
+
if gateway == network_id
|
38
|
+
invalid_gateway(network_name, "can't be the network id")
|
39
|
+
end
|
40
|
+
if gateway == broadcast
|
41
|
+
invalid_gateway(network_name, "can't be the broadcast IP")
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
dns_manager = DnsManager.create
|
46
|
+
dns_spec = safe_property(subnet_spec, 'dns', :class => Array, :optional => true)
|
47
|
+
dns = dns_manager.dns_servers(network_name, dns_spec)
|
48
|
+
|
49
|
+
availability_zone_names = parse_availability_zones(subnet_spec, network_name, availability_zones)
|
50
|
+
|
51
|
+
cloud_properties = safe_property(subnet_spec, "cloud_properties", class: Hash, default: {})
|
52
|
+
|
53
|
+
reserved_property = safe_property(subnet_spec, "reserved", :optional => true)
|
54
|
+
static_property = safe_property(subnet_spec, "static", :optional => true)
|
55
|
+
|
56
|
+
restricted_ips = Set.new
|
57
|
+
restricted_ips.add(gateway.to_i) if gateway
|
58
|
+
restricted_ips.add(network_id.to_i)
|
59
|
+
restricted_ips.add(broadcast.to_i)
|
60
|
+
|
61
|
+
each_ip(reserved_property) do |ip|
|
62
|
+
unless range.contains?(ip)
|
63
|
+
raise NetworkReservedIpOutOfRange,
|
64
|
+
"Reserved IP `#{format_ip(ip)}' is out of " +
|
65
|
+
"network `#{network_name}' range"
|
66
|
+
end
|
67
|
+
restricted_ips.add(ip)
|
68
|
+
end
|
69
|
+
|
70
|
+
static_ips = Set.new
|
71
|
+
each_ip(static_property) do |ip|
|
72
|
+
unless range.contains?(ip) && !restricted_ips.include?(ip)
|
73
|
+
raise NetworkStaticIpOutOfRange,
|
74
|
+
"Static IP `#{format_ip(ip)}' is out of " +
|
75
|
+
"network `#{network_name}' range"
|
76
|
+
end
|
77
|
+
static_ips.add(ip)
|
78
|
+
end
|
79
|
+
|
80
|
+
legacy_reserved_ranges.each do |cidr_range|
|
81
|
+
cidr_range.range(0, nil, Objectify: true).each do |ip|
|
82
|
+
restricted_ips.add(ip.to_i) unless static_ips.include?(ip.to_i)
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
86
|
+
new(network_name, range, gateway, dns, cloud_properties, netmask, availability_zone_names, restricted_ips, static_ips)
|
87
|
+
end
|
88
|
+
|
89
|
+
def initialize(network_name, range, gateway, dns, cloud_properties, netmask, availability_zone_names, restricted_ips, static_ips)
|
90
|
+
@network_name = network_name
|
91
|
+
@range = range
|
92
|
+
@gateway = gateway
|
93
|
+
@dns = dns
|
94
|
+
@cloud_properties = cloud_properties
|
95
|
+
@netmask = netmask
|
96
|
+
@availability_zone_names = availability_zone_names
|
97
|
+
@restricted_ips = restricted_ips
|
98
|
+
@static_ips = static_ips
|
99
|
+
end
|
100
|
+
|
101
|
+
def overlaps?(subnet)
|
102
|
+
range == subnet.range ||
|
103
|
+
range.contains?(subnet.range) ||
|
104
|
+
subnet.range.contains?(range)
|
105
|
+
end
|
106
|
+
|
107
|
+
def is_reservable?(ip)
|
108
|
+
range.contains?(ip) && !restricted_ips.include?(ip.to_i)
|
109
|
+
end
|
110
|
+
|
111
|
+
private
|
112
|
+
|
113
|
+
def self.parse_availability_zones(subnet_spec, network_name, availability_zones)
|
114
|
+
has_availability_zones_key = subnet_spec.has_key?('azs')
|
115
|
+
has_availability_zone_key = subnet_spec.has_key?('az')
|
116
|
+
if has_availability_zones_key && has_availability_zone_key
|
117
|
+
raise Bosh::Director::NetworkInvalidProperty, "Network '#{network_name}' contains both 'az' and 'azs'. Choose one."
|
118
|
+
end
|
119
|
+
|
120
|
+
if has_availability_zones_key
|
121
|
+
zones = safe_property(subnet_spec, 'azs', class: Array, optional: true)
|
122
|
+
if zones.empty?
|
123
|
+
raise Bosh::Director::NetworkInvalidProperty, "Network '#{network_name}' refers to an empty 'azs' array"
|
124
|
+
end
|
125
|
+
zones.each do |zone|
|
126
|
+
check_validity_of_subnet_availability_zone(zone, availability_zones, network_name)
|
127
|
+
end
|
128
|
+
zones
|
129
|
+
else
|
130
|
+
availability_zone_name = safe_property(subnet_spec, 'az', class: String, optional: true)
|
131
|
+
check_validity_of_subnet_availability_zone(availability_zone_name, availability_zones, network_name)
|
132
|
+
availability_zone_name.nil? ? nil : [availability_zone_name]
|
133
|
+
end
|
134
|
+
end
|
135
|
+
|
136
|
+
def self.invalid_gateway(network_name, reason)
|
137
|
+
raise NetworkInvalidGateway,
|
138
|
+
"Invalid gateway for network `#{network_name}': #{reason}"
|
139
|
+
end
|
140
|
+
|
141
|
+
def self.check_validity_of_subnet_availability_zone(availability_zone_name, availability_zones, network_name)
|
142
|
+
unless availability_zone_name.nil? || availability_zones.any? { |az| az.name == availability_zone_name }
|
143
|
+
raise Bosh::Director::NetworkSubnetUnknownAvailabilityZone, "Network '#{network_name}' refers to an unknown availability zone '#{availability_zone_name}'"
|
144
|
+
end
|
145
|
+
end
|
146
|
+
end
|
147
|
+
end
|
148
|
+
end
|
@@ -5,14 +5,10 @@ module Bosh::Director
|
|
5
5
|
##
|
6
6
|
# Represents a logical deployment network.
|
7
7
|
class Network
|
8
|
-
include DnsHelper
|
9
8
|
include ValidationHelper
|
10
9
|
|
11
10
|
VALID_DEFAULTS = %w(dns gateway).sort
|
12
11
|
|
13
|
-
# @return [DeploymentPlan] associated deployment
|
14
|
-
attr_accessor :deployment
|
15
|
-
|
16
12
|
# @return [String] network name
|
17
13
|
attr_accessor :name
|
18
14
|
|
@@ -24,39 +20,10 @@ module Bosh::Director
|
|
24
20
|
#
|
25
21
|
# @param [DeploymentPlan] deployment associated deployment plan
|
26
22
|
# @param [Hash] network_spec parsed deployment manifest network section
|
27
|
-
def initialize(
|
28
|
-
@
|
29
|
-
@
|
30
|
-
@
|
31
|
-
end
|
32
|
-
|
33
|
-
##
|
34
|
-
# Reserves a network resource, raises an error if reservation failed
|
35
|
-
# @param [NetworkReservation] reservation Network reservation
|
36
|
-
# @param [String] origin Whoever is reserving
|
37
|
-
def reserve!(reservation, origin)
|
38
|
-
reserve(reservation)
|
39
|
-
unless reservation.reserved?
|
40
|
-
reservation.handle_error(origin)
|
41
|
-
end
|
42
|
-
end
|
43
|
-
|
44
|
-
##
|
45
|
-
# Reserves a network resource.
|
46
|
-
#
|
47
|
-
# Will update the passed in reservation if it can be fulfilled.
|
48
|
-
# @param [NetworkReservation] reservation
|
49
|
-
# @return [Boolean] true if the reservation was fulfilled
|
50
|
-
def reserve(reservation)
|
51
|
-
raise NotImplementedError, "#reserve not implemented for #{self.class}"
|
52
|
-
end
|
53
|
-
|
54
|
-
##
|
55
|
-
# Releases a previous reservation that had been fulfilled.
|
56
|
-
# @param [NetworkReservation] reservation
|
57
|
-
# @return [void]
|
58
|
-
def release(reservation)
|
59
|
-
raise NotImplementedError, "#release not implemented for #{self.class}"
|
23
|
+
def initialize(name, logger)
|
24
|
+
@name = name
|
25
|
+
@canonical_name = Canonicalizer.canonicalize(@name)
|
26
|
+
@logger = logger
|
60
27
|
end
|
61
28
|
|
62
29
|
##
|
@@ -65,10 +32,54 @@ module Bosh::Director
|
|
65
32
|
# @param [NetworkReservation] reservation
|
66
33
|
# @param [Array<String>] default_properties
|
67
34
|
# @return [Hash] network settings that will be passed to the BOSH Agent
|
68
|
-
def network_settings(reservation, default_properties = VALID_DEFAULTS)
|
35
|
+
def network_settings(reservation, default_properties = VALID_DEFAULTS, availability_zone = nil)
|
69
36
|
raise NotImplementedError,
|
70
37
|
"#network_settings not implemented for #{self.class}"
|
71
38
|
end
|
39
|
+
|
40
|
+
def has_azs?(az_names)
|
41
|
+
raise NotImplementedError
|
42
|
+
end
|
43
|
+
|
44
|
+
def find_az_names_for_ip(ip)
|
45
|
+
raise NotImplementedError
|
46
|
+
end
|
47
|
+
|
48
|
+
def validate_reference_from_job!(job_network_spec, job_name)
|
49
|
+
end
|
50
|
+
|
51
|
+
def supports_azs?
|
52
|
+
false
|
53
|
+
end
|
54
|
+
|
55
|
+
def manual?
|
56
|
+
false
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
class NetworkWithSubnets < Network
|
61
|
+
def has_azs?(az_names)
|
62
|
+
az_names = [az_names].flatten
|
63
|
+
|
64
|
+
if az_names.compact.empty? && availability_zones.empty?
|
65
|
+
return true
|
66
|
+
end
|
67
|
+
|
68
|
+
unreferenced_zones = az_names - availability_zones
|
69
|
+
if unreferenced_zones.empty?
|
70
|
+
return true
|
71
|
+
end
|
72
|
+
|
73
|
+
false
|
74
|
+
end
|
75
|
+
|
76
|
+
def supports_azs?
|
77
|
+
true
|
78
|
+
end
|
79
|
+
|
80
|
+
def availability_zones
|
81
|
+
@subnets.map(&:availability_zone_names).flatten.uniq
|
82
|
+
end
|
72
83
|
end
|
73
84
|
end
|
74
|
-
end
|
85
|
+
end
|
@@ -0,0 +1,4 @@
|
|
1
|
+
require 'bosh/director/deployment_plan/network_planner/plan'
|
2
|
+
require 'bosh/director/deployment_plan/network_planner/planner'
|
3
|
+
require 'bosh/director/deployment_plan/network_planner/reservation_reconciler'
|
4
|
+
require 'bosh/director/deployment_plan/network_planner/vip_static_ips_planner'
|
@@ -0,0 +1,26 @@
|
|
1
|
+
module Bosh::Director::DeploymentPlan
|
2
|
+
module NetworkPlanner
|
3
|
+
class Plan
|
4
|
+
def initialize(attrs)
|
5
|
+
@reservation = attrs.fetch(:reservation)
|
6
|
+
@obsolete = attrs.fetch(:obsolete, false)
|
7
|
+
@existing = attrs.fetch(:existing, false)
|
8
|
+
end
|
9
|
+
|
10
|
+
attr_reader :reservation
|
11
|
+
attr_accessor :existing
|
12
|
+
|
13
|
+
def obsolete?
|
14
|
+
!!@obsolete
|
15
|
+
end
|
16
|
+
|
17
|
+
def desired?
|
18
|
+
!existing? && !obsolete?
|
19
|
+
end
|
20
|
+
|
21
|
+
def existing?
|
22
|
+
!!@existing
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
module Bosh::Director::DeploymentPlan
|
2
|
+
module NetworkPlanner
|
3
|
+
class Planner
|
4
|
+
def initialize(logger)
|
5
|
+
@logger = logger
|
6
|
+
end
|
7
|
+
|
8
|
+
def network_plan_with_dynamic_reservation(instance_plan, job_network)
|
9
|
+
reservation = Bosh::Director::DesiredNetworkReservation.new_dynamic(instance_plan.instance, job_network.deployment_network)
|
10
|
+
@logger.debug("Creating new dynamic reservation #{reservation} for instance '#{instance_plan.instance}'")
|
11
|
+
Plan.new(reservation: reservation)
|
12
|
+
end
|
13
|
+
|
14
|
+
def network_plan_with_static_reservation(instance_plan, job_network, static_ip)
|
15
|
+
reservation = Bosh::Director::DesiredNetworkReservation.new_static(instance_plan.instance, job_network.deployment_network, static_ip)
|
16
|
+
@logger.debug("Creating new static reservation #{reservation} for instance '#{instance_plan.instance}'")
|
17
|
+
Plan.new(reservation: reservation)
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,81 @@
|
|
1
|
+
module Bosh::Director::DeploymentPlan
|
2
|
+
module NetworkPlanner
|
3
|
+
class ReservationReconciler
|
4
|
+
def initialize(instance_plan, logger)
|
5
|
+
@instance_plan = instance_plan
|
6
|
+
@logger = logger
|
7
|
+
end
|
8
|
+
|
9
|
+
def reconcile(existing_reservations)
|
10
|
+
unplaced_existing_reservations = Set.new(existing_reservations)
|
11
|
+
existing_network_plans = []
|
12
|
+
desired_reservations = @instance_plan.network_plans.map{ |np| np.reservation }
|
13
|
+
|
14
|
+
desired_network_plans = desired_reservations.map do |reservation|
|
15
|
+
Plan.new(reservation: reservation)
|
16
|
+
end
|
17
|
+
|
18
|
+
existing_reservations.each do |existing_reservation|
|
19
|
+
unless az_is_desired(existing_reservation)
|
20
|
+
@logger.debug("Can't reuse reservation #{existing_reservation}, existing reservation az does not match desired az '#{@instance_plan.desired_instance.availability_zone}'")
|
21
|
+
next
|
22
|
+
end
|
23
|
+
|
24
|
+
desired_reservation = desired_reservations.find do |reservation|
|
25
|
+
reservation.network == existing_reservation.network &&
|
26
|
+
(reservation.dynamic? || reservation.ip == existing_reservation.ip)
|
27
|
+
end
|
28
|
+
|
29
|
+
if desired_reservation && existing_reservation.reserved?
|
30
|
+
@logger.debug("For desired reservation #{desired_reservation} found existing reservation on the same network #{existing_reservation}")
|
31
|
+
|
32
|
+
if both_are_dynamic_reservations(existing_reservation, desired_reservation) ||
|
33
|
+
both_are_static_reservations_with_same_ip(existing_reservation, desired_reservation)
|
34
|
+
|
35
|
+
@logger.debug("Reusing existing reservation #{existing_reservation} for '#{desired_reservation}'")
|
36
|
+
existing_network_plans << Plan.new(reservation: existing_reservation, existing: true)
|
37
|
+
unplaced_existing_reservations.delete(existing_reservation)
|
38
|
+
desired_network_plans.delete_if { |plan| plan.reservation == desired_reservation }
|
39
|
+
else
|
40
|
+
@logger.debug("Can't reuse reservation #{existing_reservation} for #{desired_reservation}")
|
41
|
+
end
|
42
|
+
else
|
43
|
+
@logger.debug("Unneeded reservation #{existing_reservation}")
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
obsolete_network_plans = unplaced_existing_reservations.map do |reservation|
|
48
|
+
Plan.new(reservation: reservation, obsolete: true)
|
49
|
+
end
|
50
|
+
|
51
|
+
existing_network_plans + desired_network_plans + obsolete_network_plans
|
52
|
+
end
|
53
|
+
|
54
|
+
private
|
55
|
+
|
56
|
+
def both_are_dynamic_reservations(existing_reservation, reservation)
|
57
|
+
existing_reservation.type == reservation.type &&
|
58
|
+
reservation.dynamic?
|
59
|
+
end
|
60
|
+
|
61
|
+
def both_are_static_reservations_with_same_ip(existing_reservation, reservation)
|
62
|
+
existing_reservation.type == reservation.type &&
|
63
|
+
reservation.static? &&
|
64
|
+
reservation.ip == existing_reservation.ip
|
65
|
+
end
|
66
|
+
|
67
|
+
def az_is_desired(existing_reservation)
|
68
|
+
return true unless existing_reservation.network.supports_azs?
|
69
|
+
|
70
|
+
ip_az_names = existing_reservation.network.find_az_names_for_ip(existing_reservation.ip)
|
71
|
+
@logger.debug("Reservation #{existing_reservation} belongs to azs: #{ip_az_names}")
|
72
|
+
|
73
|
+
desired_az = @instance_plan.desired_instance.az
|
74
|
+
return true if ip_az_names.to_a.compact.empty? && desired_az.nil?
|
75
|
+
return false if desired_az.nil?
|
76
|
+
|
77
|
+
ip_az_names.to_a.include?(desired_az.name)
|
78
|
+
end
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
module Bosh::Director::DeploymentPlan
|
2
|
+
module NetworkPlanner
|
3
|
+
class VipStaticIpsPlanner
|
4
|
+
def initialize(network_planner, logger)
|
5
|
+
@network_planner = network_planner
|
6
|
+
@logger = logger
|
7
|
+
end
|
8
|
+
|
9
|
+
def add_vip_network_plans(instance_plans, vip_networks)
|
10
|
+
vip_networks.each do |vip_network|
|
11
|
+
static_ips = vip_network.static_ips.dup
|
12
|
+
|
13
|
+
unplaced_instance_plans = []
|
14
|
+
instance_plans.each do |instance_plan|
|
15
|
+
static_ip = get_instance_static_ip(instance_plan.existing_instance, vip_network.name, static_ips)
|
16
|
+
if static_ip
|
17
|
+
instance_plan.network_plans << @network_planner.network_plan_with_static_reservation(instance_plan, vip_network, static_ip)
|
18
|
+
else
|
19
|
+
unplaced_instance_plans << instance_plan
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
unplaced_instance_plans.each do |instance_plan|
|
24
|
+
static_ip = static_ips.shift
|
25
|
+
instance_plan.network_plans << @network_planner.network_plan_with_static_reservation(instance_plan, vip_network, static_ip)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
private
|
31
|
+
|
32
|
+
def get_instance_static_ip(existing_instance, network_name, static_ips)
|
33
|
+
if existing_instance
|
34
|
+
existing_instance_ip = find_ip_for_network(existing_instance, network_name)
|
35
|
+
if existing_instance_ip && static_ips.include?(existing_instance_ip)
|
36
|
+
static_ips.delete(existing_instance_ip)
|
37
|
+
return existing_instance_ip
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
def find_ip_for_network(existing_instance, network_name)
|
43
|
+
ip_address = existing_instance.ip_addresses.find do |ip_address|
|
44
|
+
ip_address.network_name == network_name
|
45
|
+
end
|
46
|
+
ip_address.address if ip_address
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|