lib/judo/server.rb in judo-0.3.6 vs lib/judo/server.rb in judo-0.3.7
- old
+ new
@@ -1,23 +1,23 @@
module Judo
class Server
- attr_accessor :id,:group_name
+ attr_accessor :id
def initialize(base, id, group, version = nil)
@base = base
@id = id
- @group_name = group
+ @group = group
+ @judo_domain = base.domain
end
def create(name, options)
raise JudoError, "no group specified" unless group_name
options[:virgin] = true if options[:virgin].nil?
snapshots = options[:snapshots]
- note = options[:note] ## a user defined note field
- data = options[:data] ## instance specific data passed in JUDO_DATA
+ metadata = options[:metadata]
ip = options[:elastic_ip] ## if the ip was allocated beforehand
virgin = options[:virgin] ## should the server init?
clone = options[:clone] ## if it was cloned from a snapshot
version = options[:version]
@@ -25,40 +25,65 @@
raise JudoError, "there is already a server named #{name}" if @base.servers.detect { |s| s.name == name and s != self}
raise JudoError, "there is already a server with id #{id}" if @base.servers.detect { |s| s.id == id and s != self}
task("Creating server #{name}") do
- update "name" => name, "group" => group_name,
- "note" => note, "virgin" => virgin,
+ update("name" => name, "group" => group_name,
+ "virgin" => virgin, "elastic_ip" => ip,
"secret" => new_secret, "version" => version,
- "data" => data, "elastic_ip" => ip,
- "clone" => clone, "created_at" => Time.now.to_i
+ "clone" => clone, "created_at" => Time.now.to_i)
+ set_metadata(metadata) if metadata
@base.sdb.put_attributes(@base.base_domain, "groups", group_name => id)
end
allocate_disk(snapshots)
allocate_ip
self
end
+ def set_metadata(new_metadata)
+ puts new_metadata.inspect
+ clean_metadata = new_metadata.inject({}) { |buf,(k,v)|
+ puts [ buf, k , v ].inspect
+ buf[k.to_s] = v.to_s; buf }
+ puts clean_metadata.inspect
+ keys_to_remove = clean_metadata.keys - clean_metadata.keys
+ @metadata = clean_metadata
+ update encode_metadata(clean_metadata) unless clean_metadata.empty?
+ keys_to_remove.each { |key| remove key }
+ end
+
+ def encode_metadata(data)
+ data.inject({}) { |buf,(key,value)| buf["metadata_#{key.to_s}"] = [value].to_json; buf }
+ end
+
+ def metadata
+ @metadata ||= get_metadata
+ end
+
+ def get_metadata
+ state.inject({}) do |buf,(key,value)|
+ if key =~ /^metadata_(.*)/
+ buf[$1] = JSON.load(value.first)
+ end
+ buf
+ end
+ end
+
def group
- @group ||= @base.groups.detect { |g| g.name == group_name }
+ @group_obj ||= @base.groups.detect { |g| g.name == @group }
end
def fetch_state
@base.sdb.get_attributes(@base.server_domain, id)[:attributes]
end
def state
@base.servers_state[id] ||= fetch_state
end
- def get(key)
- state[key] && [state[key]].flatten.first
- end
-
def created_at
Time.at(get("created_at").to_i)
end
def started_at
@@ -123,10 +148,14 @@
def cloned?
!!clone
end
+ def first_boot?
+ virgin?
+ end
+
def virgin?
get("virgin").to_s == "true" ## I'm going to set it to true and it will come back from the db as "true" -> could be "false" or false or nil also
end
def secret
@@ -139,10 +168,16 @@
def volumes
(state["volumes"] || []).inject({}) { |out, kv| k, v = kv.split(':'); out[k] = v; out }
end
+######## begin simple DB access #######
+
+ def get(key)
+ state[key] && [state[key]].flatten.first
+ end
+
def update(attrs)
@base.sdb.put_attributes(@base.server_domain, id, attrs, :replace)
state.merge! attrs
end
@@ -168,15 +203,15 @@
######## end simple DB access #######
def instance_type
## need instance_size to be backward compatible - needed for configs made before v 0.3.0
- get("instance_type") || config["instance_type"] || config["instance_size"]
+ get("instance_type") || config["instance_type"] || config["instance_size"] || "m1.small"
end
def config
- group.config
+ group.config(version)
end
def to_s
"#{name}:#{group_name}"
end
@@ -293,18 +328,19 @@
## other options are "terminated" and "nil"
["pending", "running", "shutting_down", "degraded"].include?(ec2_state)
end
def start(options = {})
+ @boot= options[:boot]
new_version = options[:version]
set_instance_type(options[:instance_type]) if options[:instance_type]
invalid "Already running" if running?
invalid "No config has been commited yet, type 'judo commit'" unless group.version > 0
task("Updating server version") { update_version(options[:version]) } if options[:version]
- task("Starting server #{name}") { launch_ec2(options[:boot]) }
+ task("Starting server #{name}") { launch_ec2 }
task("Wait for server") { wait_for_running } if elastic_ip or has_volumes?
task("Attaching ip") { attach_ip } if elastic_ip
task("Attaching volumes") { attach_volumes } if has_volumes?
end
@@ -342,15 +378,15 @@
wait_for_volumes_detached if volumes.size > 0
remove "instance_id"
update "stopped_at" => Time.now.to_i
end
- def launch_ec2(boot = nil)
+ def launch_ec2
# validate
## EC2 launch_instances
- ud = user_data(boot)
+ ud = user_data
debug(ud)
result = @base.ec2.launch_instances(ami,
:instance_type => instance_type,
:availability_zone => config["availability_zone"],
:key_name => @base.key_name,
@@ -359,11 +395,13 @@
update "instance_id" => result[:aws_instance_id], "virgin" => false, "started_at" => Time.now.to_i
end
def debug(str)
return unless ENV['JUDO_DEBUG'] == "1"
- puts "<JUDO_DEBUG>#{str}</JUDO_DEBUG>"
+ puts "<DEBUG>"
+ puts str
+ puts "</DEBUG>"
end
def security_groups
[ config["security_group"] ].flatten
end
@@ -514,35 +552,24 @@
def reload
@base.reload_ec2_instances
@base.servers_state.delete(id)
end
- def user_data(judo_boot = nil)
- <<USER_DATA
-#!/bin/sh
-
-export DEBIAN_FRONTEND="noninteractive"
-export DEBIAN_PRIORITY="critical"
-export JUDO_ID='#{id}'
-export JUDO_NAME='#{name}'
-export JUDO_DOMAIN='#{@base.domain}'
-export JUDO_BOOT='#{judo_boot}'
-export JUDO_DATA='#{data}'
-export SECRET='#{secret}'
-apt-get update
-apt-get install ruby rubygems ruby-dev irb libopenssl-ruby libreadline-ruby -y
-gem install kuzushi --no-rdoc --no-ri
-GEM_BIN=`ruby -r rubygems -e "puts Gem.bindir"`
-echo "$GEM_BIN/kuzushi #{virgin? && "init" || "start"} '#{url}'" > /var/log/kuzushi.log
-$GEM_BIN/kuzushi #{virgin? && "init" || "start"} '#{url}' >> /var/log/kuzushi.log 2>&1
-USER_DATA
+ def user_data
+ erb = group.userdata(version)
+ debug erb
+ ERB.new(erb, 0, '<>').result(binding)
end
def url
- @url ||= group.s3_url
+ group.s3_url
end
+ def domain
+ @base.domain
+ end
+
def validate
### EC2 create_security_group
@base.create_security_group
### EC2 desctibe_key_pairs
@@ -594,14 +621,22 @@
other.update "name" => name1
end
end
def <=>(s)
- [group.name, name] <=> [s.group.name, s.name]
+ [group.to_s, name.to_s] <=> [s.group.to_s, s.name.to_s]
end
def new_secret
rand(2 ** 128).to_s(36)
+ end
+
+ def group_name
+ @group
+ end
+
+ def boot
+ @boot || {}
end
end
end