ironfan 4.7.2 → 4.7.3

Sign up to get free protection for your applications and to get access to all the features.
data/CHANGELOG.md CHANGED
@@ -1,3 +1,8 @@
1
+ # v4.7.3
2
+ * cluster ssh was broken for VPC instances, this will fix a few bugs (fixes #236, thanks @gwilton)
3
+ * cluster_ssh & cluster_launch: cleaning up SSH usage to handle VPC
4
+ * Enhanced IP enhanced: adds auto_elastic_ip DSL and detection, mutually exclusive with regular elastic_ip (thanks @schade)
5
+
1
6
  # v4.7.2
2
7
  * elastic_ip: ensuring that elastic IPs work with VPC instances (thanks @schade)
3
8
 
data/VERSION CHANGED
@@ -1 +1 @@
1
- 4.7.2
1
+ 4.7.3
data/ironfan.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = "ironfan"
8
- s.version = "4.7.2"
8
+ s.version = "4.7.3"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Infochimps"]
12
- s.date = "2013-01-10"
12
+ s.date = "2013-01-14"
13
13
  s.description = "Ironfan allows you to orchestrate not just systems but clusters of machines. It includes a powerful layer on top of knife and a collection of cloud cookbooks."
14
14
  s.email = "coders@infochimps.com"
15
15
  s.extra_rdoc_files = [
@@ -115,7 +115,8 @@ class Chef
115
115
  # Try SSH
116
116
  unless config[:dry_run]
117
117
  Ironfan.step(computer.name, 'trying ssh', :white)
118
- nil until tcp_test_ssh(computer.machine.dns_name){ sleep @initial_sleep_delay ||= 10 }
118
+ address = computer.machine.vpc_id.nil? ? computer.machine.public_target : computer.machine.public_ip_address
119
+ nil until tcp_test_ssh(address){ sleep @initial_sleep_delay ||= 10 }
119
120
  end
120
121
 
121
122
  Ironfan.step(computer.name, 'final provisioning', :white)
@@ -128,22 +129,25 @@ class Chef
128
129
  end
129
130
  end
130
131
 
131
- def tcp_test_ssh(hostname)
132
- tcp_socket = TCPSocket.new(hostname, 22)
132
+ def tcp_test_ssh(target)
133
+ tcp_socket = TCPSocket.new(target, 22)
133
134
  readable = IO.select([tcp_socket], nil, nil, 5)
134
135
  if readable
135
- Chef::Log.debug("sshd accepting connections on #{hostname}, banner is #{tcp_socket.gets}")
136
+ Chef::Log.debug("sshd accepting connections on #{target}, banner is #{tcp_socket.gets}")
136
137
  yield
137
138
  true
138
139
  else
139
140
  false
140
141
  end
141
142
  rescue Errno::ETIMEDOUT
143
+ Chef::Log.debug("ssh to #{target} timed out")
142
144
  false
143
145
  rescue Errno::ECONNREFUSED
146
+ Chef::Log.debug("ssh connection to #{target} refused")
144
147
  sleep 2
145
148
  false
146
149
  rescue Errno::EHOSTUNREACH
150
+ Chef::Log.debug("ssh host #{target} unreachable")
147
151
  sleep 2
148
152
  false
149
153
  ensure
@@ -47,11 +47,9 @@ class Chef
47
47
 
48
48
  config[:attribute] ||= Chef::Config[:knife][:ssh_address_attribute] || "fqdn"
49
49
  config[:ssh_user] ||= Chef::Config[:knife][:ssh_user]
50
- # config[:identity_file] ||= target.ssh_identity_file
51
50
 
52
- # @action_nodes = target.chef_nodes
53
51
  target = target.select {|t| not t.bogus? }
54
- addresses = target.map {|c| c.machine.public_hostname }.compact
52
+ addresses = target.map {|c| c.machine.vpc_id.nil? ? c.machine.public_hostname : c.machine.public_ip_address }.compact
55
53
 
56
54
  (ui.fatal("No nodes returned from search!"); exit 10) if addresses.nil? || addresses.length == 0
57
55
 
@@ -26,6 +26,8 @@ module Ironfan
26
26
  magic :placement_group, String
27
27
  magic :provider, Whatever, :default => Ironfan::Provider::Ec2
28
28
  magic :elastic_ip, String
29
+ magic :auto_elastic_ip, String
30
+ magic :allocation_id, String
29
31
  magic :region, String, :default => ->{ default_region }
30
32
  collection :security_groups, Ironfan::Dsl::Ec2::SecurityGroup, :key_method => :name
31
33
  magic :ssh_user, String, :default => ->{ image_info[:ssh_user] }
@@ -4,11 +4,11 @@ module Ironfan
4
4
 
5
5
  class ElasticIp < Ironfan::Provider::Resource
6
6
  delegate :addresses, :associate_address, :allocation_id,
7
- :allocation_id=, :destroy, :domain, :domain=,
8
- :describe_addresses, :disassociate_address, :domain, :id,
9
- :network_interface_id, :network_interface_id=, :public_ip,
10
- :public_ip=, :public_ip_address, :save, :server=, :server, :server_id,
11
- :server_id=,
7
+ :allocation_id=, :allocate_address, :auto_elastic_ip, :destroy,
8
+ :domain, :domain=, :describe_addresses, :disassociate_address,
9
+ :domain, :id, :network_interface_id, :network_interface_id=,
10
+ :public_ip, :public_ip=, :public_ip_address, :save, :server=,
11
+ :server, :server_id, :server_id=,
12
12
  :to => :adaptee
13
13
 
14
14
  def self.shared?() true; end
@@ -30,7 +30,12 @@ module Ironfan
30
30
  # is passed to knife and aids in troubleshooting any refusal to
31
31
  # attach Elastic IPs
32
32
  Chef::Log.debug( "AWS domain: #{eip.domain}" )
33
- Chef::Log.debug( "available ip match: #{eip.public_ip}" )
33
+ if eip.public_ip.nil?
34
+ Chef::Log.debug( "no Elastic IPs currently allocated" )
35
+ else
36
+ Chef::Log.debug( "available ip match: #{eip.public_ip}" )
37
+ Chef::Log.debug( "available allocation_id match: #{eip.allocation_id}" )
38
+ end
34
39
  Chef::Log.debug( "----------------------" )
35
40
  end
36
41
 
@@ -53,6 +58,32 @@ module Ironfan
53
58
  return unless computer.created?
54
59
  return unless elastic_ip = computer.server.ec2.elastic_ip
55
60
  return unless recall? elastic_ip
61
+ # also, in the case of VPC Elastic IPs, can discover and use allocation_id to attach a VPC Elastic IP.
62
+ return unless computer.server.ec2.include?(:elastic_ip)
63
+ if ( computer.server.ec2.elastic_ip.nil? and cloud.vpc.nil? )
64
+ # First, :elastic_ip is set, no address is currently allocated for this connection's owner
65
+ # NOTE: We cannot specify an address to create, but after a reload we can then load the first available.
66
+ if computer.server.addresses.nil?
67
+ Ec2.connection.allocate_address
68
+ load!
69
+ elastic_ip = computer.server.addresses.first.public_ip
70
+ Chef::Log.debug( "allocating new Elastic IP address" )
71
+ else
72
+ # Second, :elastic_ip is set, has an address available to use but has no set value available in facet definition.
73
+ elastic_ip = computer.server.addresses.first.public_ip
74
+ Chef::Log.debug( "using first available Elastic IP address" )
75
+ end
76
+ elsif ( !computer.server.ec2.elastic_ip.nil? or cloud.vpc.nil? )
77
+ # Third, :elastic_ip is set, has an address available to use, has a set value in facet definition and is not VPC.
78
+ elastic_ip = computer.server.ec2.elastic_ip
79
+ Chef::Log.debug( "using requested Elastic IP address" )
80
+ elsif ( computer.server.ec2.elastic_ip.nil? and !cloud.vpc.nil? )
81
+ # Fourth, is exactly like Third but on a VPC domain. (this is functionaility for attaching VPC Elastic IPS)
82
+ allocation_id = computer.server.ec2.allocation_id
83
+ Chef::Log.debug( "using Elastic IP address matched to given Allocation ID" )
84
+ else
85
+ ui.fatal("You have set both :elastic_ip and :auto_elastic_ip in your facet definition; which are mutually exclusive.")
86
+ end
56
87
  Ironfan.step(computer.name, "associating Elastic IP #{elastic_ip}", :blue)
57
88
  Ironfan.unless_dry_run do
58
89
  Ironfan.safely do
metadata CHANGED
@@ -2,7 +2,7 @@
2
2
  name: ironfan
3
3
  version: !ruby/object:Gem::Version
4
4
  prerelease:
5
- version: 4.7.2
5
+ version: 4.7.3
6
6
  platform: ruby
7
7
  authors:
8
8
  - Infochimps
@@ -10,7 +10,7 @@ autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
12
 
13
- date: 2013-01-10 00:00:00 Z
13
+ date: 2013-01-14 00:00:00 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: chef
@@ -282,7 +282,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
282
282
  requirements:
283
283
  - - ">="
284
284
  - !ruby/object:Gem::Version
285
- hash: -3116104857531814331
285
+ hash: 240697130002937334
286
286
  segments:
287
287
  - 0
288
288
  version: "0"