auser-poolparty 0.0.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGELOG +12 -0
- data/Manifest +115 -0
- data/README.txt +140 -0
- data/Rakefile +27 -0
- data/bin/instance +61 -0
- data/bin/pool +62 -0
- data/config/cloud_master_takeover +17 -0
- data/config/create_proxy_ami.sh +582 -0
- data/config/haproxy.conf +29 -0
- data/config/heartbeat.conf +8 -0
- data/config/heartbeat_authkeys.conf +2 -0
- data/config/installers/ubuntu_install.sh +77 -0
- data/config/monit/haproxy.monit.conf +7 -0
- data/config/monit/nginx.monit.conf +0 -0
- data/config/monit.conf +9 -0
- data/config/nginx.conf +24 -0
- data/config/reconfigure_instances_script.sh +18 -0
- data/config/sample-config.yml +23 -0
- data/config/scp_instances_script.sh +12 -0
- data/lib/core/array.rb +13 -0
- data/lib/core/exception.rb +9 -0
- data/lib/core/float.rb +13 -0
- data/lib/core/hash.rb +11 -0
- data/lib/core/kernel.rb +12 -0
- data/lib/core/module.rb +22 -0
- data/lib/core/object.rb +18 -0
- data/lib/core/proc.rb +15 -0
- data/lib/core/string.rb +49 -0
- data/lib/core/time.rb +41 -0
- data/lib/modules/callback.rb +133 -0
- data/lib/modules/ec2_wrapper.rb +82 -0
- data/lib/modules/safe_instance.rb +31 -0
- data/lib/modules/vlad_override.rb +82 -0
- data/lib/poolparty/application.rb +170 -0
- data/lib/poolparty/init.rb +6 -0
- data/lib/poolparty/master.rb +329 -0
- data/lib/poolparty/monitors/cpu.rb +19 -0
- data/lib/poolparty/monitors/memory.rb +26 -0
- data/lib/poolparty/monitors/web.rb +23 -0
- data/lib/poolparty/monitors.rb +13 -0
- data/lib/poolparty/optioner.rb +16 -0
- data/lib/poolparty/plugin.rb +43 -0
- data/lib/poolparty/plugin_manager.rb +67 -0
- data/lib/poolparty/provider/packages/essential.rb +6 -0
- data/lib/poolparty/provider/packages/git.rb +4 -0
- data/lib/poolparty/provider/packages/haproxy.rb +20 -0
- data/lib/poolparty/provider/packages/heartbeat.rb +4 -0
- data/lib/poolparty/provider/packages/monit.rb +6 -0
- data/lib/poolparty/provider/packages/rsync.rb +4 -0
- data/lib/poolparty/provider/packages/ruby.rb +37 -0
- data/lib/poolparty/provider/packages/s3fuse.rb +11 -0
- data/lib/poolparty/provider/provider.rb +60 -0
- data/lib/poolparty/provider.rb +2 -0
- data/lib/poolparty/remote_instance.rb +216 -0
- data/lib/poolparty/remoter.rb +106 -0
- data/lib/poolparty/remoting.rb +112 -0
- data/lib/poolparty/scheduler.rb +103 -0
- data/lib/poolparty/tasks/cloud.rake +57 -0
- data/lib/poolparty/tasks/development.rake +38 -0
- data/lib/poolparty/tasks/ec2.rake +20 -0
- data/lib/poolparty/tasks/instance.rake +63 -0
- data/lib/poolparty/tasks/plugins.rake +30 -0
- data/lib/poolparty/tasks/server.rake +42 -0
- data/lib/poolparty/tasks.rb +29 -0
- data/lib/poolparty/tmp.rb +46 -0
- data/lib/poolparty.rb +105 -0
- data/lib/s3/s3_object_store_folders.rb +44 -0
- data/misc/basics_tutorial.txt +142 -0
- data/poolparty.gemspec +72 -0
- data/spec/application_spec.rb +39 -0
- data/spec/callback_spec.rb +194 -0
- data/spec/core_spec.rb +15 -0
- data/spec/helpers/ec2_mock.rb +44 -0
- data/spec/kernel_spec.rb +11 -0
- data/spec/master_spec.rb +203 -0
- data/spec/monitors/cpu_monitor_spec.rb +38 -0
- data/spec/monitors/memory_spec.rb +50 -0
- data/spec/monitors/misc_monitor_spec.rb +50 -0
- data/spec/monitors/web_spec.rb +39 -0
- data/spec/optioner_spec.rb +22 -0
- data/spec/plugin_manager_spec.rb +31 -0
- data/spec/plugin_spec.rb +101 -0
- data/spec/pool_binary_spec.rb +10 -0
- data/spec/poolparty_spec.rb +15 -0
- data/spec/provider_spec.rb +17 -0
- data/spec/remote_instance_spec.rb +149 -0
- data/spec/remoter_spec.rb +65 -0
- data/spec/remoting_spec.rb +84 -0
- data/spec/scheduler_spec.rb +75 -0
- data/spec/spec_helper.rb +39 -0
- data/spec/string_spec.rb +28 -0
- data/web/static/conf/nginx.conf +22 -0
- data/web/static/site/images/balloon.png +0 -0
- data/web/static/site/images/cb.png +0 -0
- data/web/static/site/images/clouds.png +0 -0
- data/web/static/site/images/railsconf_preso_img.png +0 -0
- data/web/static/site/index.html +71 -0
- data/web/static/site/javascripts/application.js +3 -0
- data/web/static/site/javascripts/corner.js +178 -0
- data/web/static/site/javascripts/jquery-1.2.6.pack.js +11 -0
- data/web/static/site/misc.html +42 -0
- data/web/static/site/storage/pool_party_presentation.pdf +0 -0
- data/web/static/site/stylesheets/application.css +100 -0
- data/web/static/site/stylesheets/reset.css +17 -0
- data/web/static/src/layouts/application.haml +25 -0
- data/web/static/src/pages/index.haml +25 -0
- data/web/static/src/pages/misc.haml +5 -0
- data/web/static/src/stylesheets/application.sass +100 -0
- metadata +260 -0
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
#!/bin/sh
|
|
2
|
+
|
|
3
|
+
apt-get clean && apt-get update
|
|
4
|
+
|
|
5
|
+
echo 'increasing the memory for apt'
|
|
6
|
+
echo 'APT::Cache-Limit "516777216";' >> /etc/apt/apt.conf.d/70debconf
|
|
7
|
+
|
|
8
|
+
echo 'running ubuntu_install.sh'
|
|
9
|
+
rm -rf /usr/local/src/*
|
|
10
|
+
|
|
11
|
+
echo 'updating apt'
|
|
12
|
+
apt-get update
|
|
13
|
+
# Get the essentials
|
|
14
|
+
echo 'building essentials'
|
|
15
|
+
apt-get -y install build-essential
|
|
16
|
+
|
|
17
|
+
echo 'Installing git'
|
|
18
|
+
apt-get -y install git-core rsync
|
|
19
|
+
|
|
20
|
+
# Install ruby
|
|
21
|
+
echo 'Installing ruby...'
|
|
22
|
+
apt-get -y install ruby1.8-dev ruby1.8 ri1.8 rdoc1.8 irb1.8 libreadline-ruby1.8 libruby1.8
|
|
23
|
+
ln -sf /usr/bin/ruby1.8 /usr/local/bin/ruby
|
|
24
|
+
ln -sf /usr/bin/ri1.8 /usr/local/bin/ri
|
|
25
|
+
ln -sf /usr/bin/rdoc1.8 /usr/local/bin/rdoc
|
|
26
|
+
ln -sf /usr/bin/irb1.8 /usr/local/bin/irb
|
|
27
|
+
|
|
28
|
+
# Install rubygems
|
|
29
|
+
echo '-- Installing Rubygems'
|
|
30
|
+
# if [[ ! -f /usr/local/src/rubygems-1.1.1 ]]; then
|
|
31
|
+
cd /usr/local/src
|
|
32
|
+
wget http://rubyforge.org/frs/download.php/35283/rubygems-1.1.1.tgz
|
|
33
|
+
tar -xzf rubygems-1.1.1.tgz
|
|
34
|
+
rm rubygems-1.1.1.tgz
|
|
35
|
+
cd rubygems-1.1.1
|
|
36
|
+
ruby setup.rb --no-rdoc --no-ri
|
|
37
|
+
ln -sf /usr/bin/gem1.8 /usr/bin/gem
|
|
38
|
+
# fi
|
|
39
|
+
|
|
40
|
+
# Install gems
|
|
41
|
+
# if [[ which pool | grep -v "bin" ]]; then
|
|
42
|
+
gem update --system
|
|
43
|
+
gem install SQS aws-s3 amazon-ec2 aska rake poolparty --no-rdoc --no-ri --no-test
|
|
44
|
+
# fi
|
|
45
|
+
|
|
46
|
+
# Install haproxy
|
|
47
|
+
# if [[ which haproxy | grep -v "bin" ]]; then
|
|
48
|
+
apt-get -y install haproxy
|
|
49
|
+
echo 'Configuring haproxy logging'
|
|
50
|
+
sed -i 's/ENABLED=0/ENABLED=1/g' /etc/default/haproxy
|
|
51
|
+
sed -i 's/SYSLOGD=\"\"/SYSLOGD=\"-r\"/g' /etc/default/syslogd
|
|
52
|
+
echo 'local0.* /var/log/haproxy.log' >> /etc/syslog.conf && /etc/init.d/sysklogd restart
|
|
53
|
+
/etc/init.d/haproxy restart
|
|
54
|
+
# fi
|
|
55
|
+
# Install heartbeat
|
|
56
|
+
# if [[ which heartbeat | grep -v "bin" ]]; then
|
|
57
|
+
apt-get -y install heartbeat-2
|
|
58
|
+
# fi
|
|
59
|
+
|
|
60
|
+
# Install monit
|
|
61
|
+
# if [[ which monit | grep -v "bin" ]]; then
|
|
62
|
+
apt-get -y install monit
|
|
63
|
+
sudo mkdir /etc/monit
|
|
64
|
+
sed -i 's/startup=0/startup=1/g' /etc/default/monit
|
|
65
|
+
/etc/init.d/monit start
|
|
66
|
+
# fi
|
|
67
|
+
|
|
68
|
+
# Install s3fuse
|
|
69
|
+
# if [[ which s3fs | grep -v "bin" ]]; then
|
|
70
|
+
apt-get install -y libcurl4-openssl-dev libxml2-dev libfuse-dev
|
|
71
|
+
cd /usr/local/src && wget http://s3fs.googlecode.com/files/s3fs-r166-source.tar.gz
|
|
72
|
+
tar -zxf s3fs-r166-source.tar.gz
|
|
73
|
+
cd s3fs/ && make
|
|
74
|
+
mv s3fs /usr/bin
|
|
75
|
+
# fi
|
|
76
|
+
|
|
77
|
+
echo ' - installed from script!'
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
check process haproxy with pidfile /var/run/haproxy.pid
|
|
2
|
+
start program = "/usr/sbin/haproxy -f /etc/haproxy.cfg -p /var/run/haproxy.pid"
|
|
3
|
+
stop program = "/usr/bin/killall -9 haproxy"
|
|
4
|
+
if totalmem is greater than 100.0 MB for 4 cycles then restart
|
|
5
|
+
if cpu is greater than 50% for 2 cycles then alert
|
|
6
|
+
if cpu is greater than 80% for 3 cycles then restart
|
|
7
|
+
if loadavg(5min) greater than 10 for 8 cycles then restart
|
|
File without changes
|
data/config/monit.conf
ADDED
data/config/nginx.conf
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
user usr usr;
|
|
2
|
+
worker_processes 2;
|
|
3
|
+
|
|
4
|
+
http {
|
|
5
|
+
sendfile on;
|
|
6
|
+
tcp_nopush on;
|
|
7
|
+
|
|
8
|
+
keepalive_timeout 65;
|
|
9
|
+
tcp_nodelay on;
|
|
10
|
+
|
|
11
|
+
upstream fast_mongrels { server 127.0.0.1:4567; }
|
|
12
|
+
|
|
13
|
+
server {
|
|
14
|
+
listen 80;
|
|
15
|
+
server_name srv;
|
|
16
|
+
root /apps/pool-party;
|
|
17
|
+
|
|
18
|
+
location / {
|
|
19
|
+
proxy_pass http://fast_mongrels;
|
|
20
|
+
break;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
}
|
|
24
|
+
}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
#!/bin/sh
|
|
2
|
+
|
|
3
|
+
# Reconfigure master
|
|
4
|
+
:config_master
|
|
5
|
+
# Start this instance's master maintain script
|
|
6
|
+
:start_pool_maintain
|
|
7
|
+
# Make the ha.d/resource.d
|
|
8
|
+
sudo mkdir /etc/ha.d/resource.d/
|
|
9
|
+
# Set this hostname as appropriate in the cloud
|
|
10
|
+
:set_hostname
|
|
11
|
+
# Configure heartbeat
|
|
12
|
+
sudo mkdir /etc/ha.d/resource.d/
|
|
13
|
+
# Start heartbeat
|
|
14
|
+
/etc/init.d/heartbeat start
|
|
15
|
+
# Start s3fs
|
|
16
|
+
:start_s3fs
|
|
17
|
+
# Configure monit
|
|
18
|
+
mkdir /etc/monit.d
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
:app_name: "test_app"
|
|
2
|
+
:user_id: "1619-6456-1164"
|
|
3
|
+
:access_key: ""
|
|
4
|
+
:secret_access_key: ""
|
|
5
|
+
:ami: "ami-4f7a9f26"
|
|
6
|
+
:size: small
|
|
7
|
+
:polling_time: "30.seconds"
|
|
8
|
+
:minimum_instances: 2
|
|
9
|
+
:maximum_instances: 3
|
|
10
|
+
:ec2_dir: "/Users/auser/.ec2"
|
|
11
|
+
:keypair: auser
|
|
12
|
+
:os: ubuntu
|
|
13
|
+
:host_port: 80
|
|
14
|
+
:client_port: 8001
|
|
15
|
+
:shared_bucket: "pool-party-app-data"
|
|
16
|
+
:services: nginx
|
|
17
|
+
:environment: production
|
|
18
|
+
:contract_when:
|
|
19
|
+
web > 10
|
|
20
|
+
cpu < 0.2
|
|
21
|
+
:expand_when:
|
|
22
|
+
cpu > 0.45
|
|
23
|
+
web < 10
|
data/lib/core/array.rb
ADDED
data/lib/core/float.rb
ADDED
data/lib/core/hash.rb
ADDED
data/lib/core/kernel.rb
ADDED
data/lib/core/module.rb
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# Module overloads
|
|
2
|
+
class Module
|
|
3
|
+
# Gives us alias_method_chain from rails
|
|
4
|
+
def alias_method_chain(target, feature)
|
|
5
|
+
aliased_target, punctuation = target.to_s.sub(/([?!=])$/, ''), $1
|
|
6
|
+
yield(aliased_target, punctuation) if block_given?
|
|
7
|
+
|
|
8
|
+
with_method, without_method = "#{aliased_target}_with_#{feature}#{punctuation}", "#{aliased_target}_without_#{feature}#{punctuation}"
|
|
9
|
+
|
|
10
|
+
alias_method without_method, target
|
|
11
|
+
alias_method target, with_method
|
|
12
|
+
|
|
13
|
+
case
|
|
14
|
+
when public_method_defined?(without_method)
|
|
15
|
+
public target
|
|
16
|
+
when protected_method_defined?(without_method)
|
|
17
|
+
protected target
|
|
18
|
+
when private_method_defined?(without_method)
|
|
19
|
+
private target
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
data/lib/core/object.rb
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
=begin rdoc
|
|
2
|
+
Basic, add an alias_method to the object class
|
|
3
|
+
Add returning to the object
|
|
4
|
+
=end
|
|
5
|
+
class Object
|
|
6
|
+
def alias_method(new_id, original_id)
|
|
7
|
+
original = self.method(original_id).to_proc
|
|
8
|
+
define_method(new_id){|*args| original.call(*args)}
|
|
9
|
+
end
|
|
10
|
+
def returning(receiver)
|
|
11
|
+
yield receiver
|
|
12
|
+
receiver
|
|
13
|
+
end
|
|
14
|
+
def extended(&block)
|
|
15
|
+
block.in_context(self).call
|
|
16
|
+
self
|
|
17
|
+
end
|
|
18
|
+
end
|
data/lib/core/proc.rb
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
class Proc
|
|
2
|
+
def bind(object)
|
|
3
|
+
block, time = self, Time.now
|
|
4
|
+
(class << object; self; end).class_eval do
|
|
5
|
+
method_name = "__bind_#{time.to_i}_#{time.usec}"
|
|
6
|
+
define_method(method_name, &block)
|
|
7
|
+
method = instance_method(method_name)
|
|
8
|
+
remove_method(method_name)
|
|
9
|
+
method
|
|
10
|
+
end.bind(object)
|
|
11
|
+
end
|
|
12
|
+
def in_context(klass_or_obj)
|
|
13
|
+
klass_or_obj.send(:eval, self.to_ruby)
|
|
14
|
+
end
|
|
15
|
+
end
|
data/lib/core/string.rb
ADDED
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
class String
|
|
2
|
+
def hasherize(format=[])
|
|
3
|
+
hash = {}
|
|
4
|
+
i = 0
|
|
5
|
+
self.split(%r{[\n|\t|\s| ]+}).collect {|a| a.strip}.each do |f|
|
|
6
|
+
break unless format[i]
|
|
7
|
+
unless f == "" || f.nil?
|
|
8
|
+
hash[format[i]] = f
|
|
9
|
+
i+=1
|
|
10
|
+
end
|
|
11
|
+
end
|
|
12
|
+
hash
|
|
13
|
+
end
|
|
14
|
+
def ^(h={})
|
|
15
|
+
self.gsub(/:([\w]+)/) {h[$1.to_sym] if h.include?($1.to_sym)}
|
|
16
|
+
end
|
|
17
|
+
def runnable
|
|
18
|
+
self.strip.gsub(/\n/, " && ")
|
|
19
|
+
end
|
|
20
|
+
def classify
|
|
21
|
+
self.capitalize
|
|
22
|
+
end
|
|
23
|
+
def bucket_objects
|
|
24
|
+
AWS::S3::Bucket.objects(self)
|
|
25
|
+
end
|
|
26
|
+
def bucket_object(key)
|
|
27
|
+
AWS::S3::S3Object.value key, self if bucket_object_exists?(key)
|
|
28
|
+
end
|
|
29
|
+
def bucket_object_exists?(key)
|
|
30
|
+
AWS::S3::S3Object.exists? key, self
|
|
31
|
+
end
|
|
32
|
+
def store_bucket_value(key, data)
|
|
33
|
+
AWS::S3::S3Object.store key, data, self unless bucket_object_exists?(key)
|
|
34
|
+
end
|
|
35
|
+
def delete_bucket_value(key)
|
|
36
|
+
AWS::S3::S3Object.delete(key, self) if bucket_object_exists?(key)
|
|
37
|
+
end
|
|
38
|
+
def bucket_exists?
|
|
39
|
+
begin
|
|
40
|
+
AWS::S3::Bucket.find(self)
|
|
41
|
+
return true
|
|
42
|
+
rescue
|
|
43
|
+
return false
|
|
44
|
+
end
|
|
45
|
+
end
|
|
46
|
+
def delete_bucket
|
|
47
|
+
AWS::S3::Bucket.delete(self, :force => true) if bucket_exists?
|
|
48
|
+
end
|
|
49
|
+
end
|
data/lib/core/time.rb
ADDED
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
=begin rdoc
|
|
2
|
+
Based off the rails Numeric class.
|
|
3
|
+
Gives us the ability to use nice phrases such as
|
|
4
|
+
30.seconds, 5.days, etc.
|
|
5
|
+
=end
|
|
6
|
+
class Numeric
|
|
7
|
+
def ago(time = Time.now)
|
|
8
|
+
time - self
|
|
9
|
+
end
|
|
10
|
+
alias :until :ago
|
|
11
|
+
|
|
12
|
+
def since(time = Time.now)
|
|
13
|
+
time + self
|
|
14
|
+
end
|
|
15
|
+
alias :from_now :since
|
|
16
|
+
|
|
17
|
+
def seconds
|
|
18
|
+
self
|
|
19
|
+
end
|
|
20
|
+
alias :second :seconds
|
|
21
|
+
|
|
22
|
+
def minutes
|
|
23
|
+
self * 60
|
|
24
|
+
end
|
|
25
|
+
alias :minute :minutes
|
|
26
|
+
|
|
27
|
+
def hours
|
|
28
|
+
self * 60.minutes
|
|
29
|
+
end
|
|
30
|
+
alias :hour :hours
|
|
31
|
+
|
|
32
|
+
def days
|
|
33
|
+
self * 24.hours
|
|
34
|
+
end
|
|
35
|
+
alias :day :days
|
|
36
|
+
|
|
37
|
+
def weeks
|
|
38
|
+
self * 7.days
|
|
39
|
+
end
|
|
40
|
+
alias :week :weeks
|
|
41
|
+
end
|
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
=begin rdoc
|
|
2
|
+
Basic callbacks
|
|
3
|
+
=end
|
|
4
|
+
module PoolParty
|
|
5
|
+
module Callbacks
|
|
6
|
+
module ClassMethods
|
|
7
|
+
def define_callback_module(mod)
|
|
8
|
+
callbacks << mod
|
|
9
|
+
end
|
|
10
|
+
def define_callback_class(cla)
|
|
11
|
+
classes << cla
|
|
12
|
+
end
|
|
13
|
+
def callback(type, m, *args, &block)
|
|
14
|
+
arr = []
|
|
15
|
+
args.each do |arg|
|
|
16
|
+
arr << case arg.class.to_s
|
|
17
|
+
when "Hash"
|
|
18
|
+
arg.collect do |meth, klass|
|
|
19
|
+
case klass.class.to_s
|
|
20
|
+
when "String"
|
|
21
|
+
define_callback_class(klass)
|
|
22
|
+
"self.#{klass.to_s.downcase}.#{meth}(self)"
|
|
23
|
+
else
|
|
24
|
+
"#{klass}.send :#{meth}, self"
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
when "Symbol"
|
|
28
|
+
"self.send :#{arg}, self"
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
string = ""
|
|
33
|
+
if block_given?
|
|
34
|
+
num = store_proc(block.to_proc)
|
|
35
|
+
arr << <<-EOM
|
|
36
|
+
self.class.get_proc(#{num}).bind(self).call
|
|
37
|
+
EOM
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
string = create_eval_for_mod_with_string_and_type!(m, type) do
|
|
41
|
+
arr.join("\n")
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
mMode = Module.new {eval string}
|
|
45
|
+
|
|
46
|
+
define_callback_module(mMode)
|
|
47
|
+
end
|
|
48
|
+
def before(m, *args, &block)
|
|
49
|
+
callback(:before, m, *args, &block)
|
|
50
|
+
end
|
|
51
|
+
def after(m, *args, &block)
|
|
52
|
+
callback(:after, m, *args, &block)
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
def create_eval_for_mod_with_string_and_type!(meth, type=nil, &block)
|
|
56
|
+
str = ""
|
|
57
|
+
case type
|
|
58
|
+
when :before
|
|
59
|
+
str << <<-EOD
|
|
60
|
+
def #{meth}(*args)
|
|
61
|
+
#{yield}
|
|
62
|
+
super
|
|
63
|
+
end
|
|
64
|
+
EOD
|
|
65
|
+
when :after
|
|
66
|
+
str << <<-EOD
|
|
67
|
+
def #{meth}(*args)
|
|
68
|
+
super
|
|
69
|
+
#{yield}
|
|
70
|
+
end
|
|
71
|
+
EOD
|
|
72
|
+
else
|
|
73
|
+
str << <<-EOD
|
|
74
|
+
def #{meth}(*args)
|
|
75
|
+
#{yield}
|
|
76
|
+
end
|
|
77
|
+
EOD
|
|
78
|
+
end
|
|
79
|
+
str
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
def callbacks
|
|
83
|
+
@callbacks ||= []
|
|
84
|
+
end
|
|
85
|
+
def classes
|
|
86
|
+
@classes ||= []
|
|
87
|
+
end
|
|
88
|
+
end
|
|
89
|
+
|
|
90
|
+
module InstanceMethods
|
|
91
|
+
def initialize(*args)
|
|
92
|
+
extend_callbacks
|
|
93
|
+
extend_callback_methods
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
def extend_callback_methods
|
|
97
|
+
unless self.class.classes.empty?
|
|
98
|
+
self.class.classes.each do |klass|
|
|
99
|
+
m = %{def #{klass.to_s.downcase};@#{klass.to_s.downcase} ||= #{klass}.new;end}
|
|
100
|
+
self.class.class_eval m unless self.class.method_defined?(m)
|
|
101
|
+
end
|
|
102
|
+
end
|
|
103
|
+
end
|
|
104
|
+
|
|
105
|
+
def extend_callbacks
|
|
106
|
+
unless self.class.callbacks.empty?
|
|
107
|
+
self.class.callbacks.each do |mod|
|
|
108
|
+
self.extend(mod)
|
|
109
|
+
end
|
|
110
|
+
end
|
|
111
|
+
end
|
|
112
|
+
end
|
|
113
|
+
|
|
114
|
+
module ProcStoreMethods
|
|
115
|
+
def store_proc(proc)
|
|
116
|
+
proc_storage << proc
|
|
117
|
+
proc_storage.index(proc)
|
|
118
|
+
end
|
|
119
|
+
def get_proc(num)
|
|
120
|
+
proc_storage[num]
|
|
121
|
+
end
|
|
122
|
+
def proc_storage
|
|
123
|
+
@proc_store ||= []
|
|
124
|
+
end
|
|
125
|
+
end
|
|
126
|
+
|
|
127
|
+
def self.included(receiver)
|
|
128
|
+
receiver.extend ClassMethods
|
|
129
|
+
receiver.extend ProcStoreMethods
|
|
130
|
+
receiver.send :include, InstanceMethods
|
|
131
|
+
end
|
|
132
|
+
end
|
|
133
|
+
end
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
module PoolParty
|
|
2
|
+
extend self
|
|
3
|
+
|
|
4
|
+
module Ec2Wrapper
|
|
5
|
+
|
|
6
|
+
module ClassMethods
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
module InstanceMethods
|
|
10
|
+
# Run a new instance, with the user_data and the ami described in the config
|
|
11
|
+
def launch_new_instance!
|
|
12
|
+
instance = ec2.run_instances(
|
|
13
|
+
:image_id => Application.ami,
|
|
14
|
+
:user_data => "#{Application.launching_user_data}",
|
|
15
|
+
:minCount => 1,
|
|
16
|
+
:maxCount => 1,
|
|
17
|
+
:key_name => Application.keypair,
|
|
18
|
+
:size => "#{Application.size}")
|
|
19
|
+
|
|
20
|
+
item = instance.RunInstancesResponse.instancesSet.item
|
|
21
|
+
EC2ResponseObject.get_hash_from_response(item)
|
|
22
|
+
end
|
|
23
|
+
# Shutdown the instance by instance_id
|
|
24
|
+
def terminate_instance!(instance_id)
|
|
25
|
+
ec2.terminate_instances(:instance_id => instance_id)
|
|
26
|
+
end
|
|
27
|
+
def associate_address_with(ip, instance_id)
|
|
28
|
+
ec2.associate_address(:instance_id => instance_id, :public_ip => ip)
|
|
29
|
+
end
|
|
30
|
+
# Instance description
|
|
31
|
+
def describe_instance(id)
|
|
32
|
+
instance = ec2.describe_instances(:instance_id => id)
|
|
33
|
+
item = instance.DescribeInstancesResponse.reservationSet.item.instancesSet.item
|
|
34
|
+
EC2ResponseObject.get_hash_from_response(item)
|
|
35
|
+
end
|
|
36
|
+
# Get instance by id
|
|
37
|
+
def get_instance_by_id(id)
|
|
38
|
+
get_instances_description.select {|a| a.instance_id == id}[0] rescue nil
|
|
39
|
+
end
|
|
40
|
+
# Get the s3 description for the response in a hash format
|
|
41
|
+
def get_instances_description
|
|
42
|
+
@cached_descriptions ||= EC2ResponseObject.get_descriptions(ec2.describe_instances)
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
# EC2 connections
|
|
46
|
+
def ec2
|
|
47
|
+
@ec2 ||= EC2::Base.new(:access_key_id => Application.access_key, :secret_access_key => Application.secret_access_key)
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
def self.included(receiver)
|
|
52
|
+
receiver.extend ClassMethods
|
|
53
|
+
receiver.send :include, InstanceMethods
|
|
54
|
+
end
|
|
55
|
+
end
|
|
56
|
+
# Provides a simple class to wrap around the amazon responses
|
|
57
|
+
class EC2ResponseObject
|
|
58
|
+
def self.get_descriptions(resp)
|
|
59
|
+
rs = resp.DescribeInstancesResponse.reservationSet.item
|
|
60
|
+
rs = rs.respond_to?(:instancesSet) ? rs.instancesSet : rs
|
|
61
|
+
out = begin
|
|
62
|
+
rs.reject {|a| a.empty? }.collect {|r| EC2ResponseObject.get_hash_from_response(r.instancesSet.item)}.reject {|a| a.nil? }
|
|
63
|
+
rescue Exception => e
|
|
64
|
+
begin
|
|
65
|
+
# Really weird bug with amazon's ec2 gem
|
|
66
|
+
rs.reject {|a| a.empty? }.collect {|r| EC2ResponseObject.get_hash_from_response(r)}.reject {|a| a.nil? }
|
|
67
|
+
rescue Exception => e
|
|
68
|
+
[]
|
|
69
|
+
end
|
|
70
|
+
end
|
|
71
|
+
out
|
|
72
|
+
end
|
|
73
|
+
def self.get_hash_from_response(resp)
|
|
74
|
+
{
|
|
75
|
+
:instance_id => resp.instanceId,
|
|
76
|
+
:ip => resp.dnsName,
|
|
77
|
+
:status => resp.instanceState.name,
|
|
78
|
+
:launching_time => resp.launchTime
|
|
79
|
+
} rescue nil
|
|
80
|
+
end
|
|
81
|
+
end
|
|
82
|
+
end
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
=begin rdoc
|
|
2
|
+
Make a command thread-safe
|
|
3
|
+
=end
|
|
4
|
+
require "monitor"
|
|
5
|
+
module PoolParty
|
|
6
|
+
extend self
|
|
7
|
+
|
|
8
|
+
module ThreadSafeInstance
|
|
9
|
+
|
|
10
|
+
module ClassMethods
|
|
11
|
+
def make_safe(meth)
|
|
12
|
+
original_method = "_unsafe_#{meth}_"
|
|
13
|
+
alias_method original_method, meth
|
|
14
|
+
define_method(meth) {|*args| self.class.synchronize { self.send(original_method) } }
|
|
15
|
+
self
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
module InstanceMethods
|
|
20
|
+
def make_safe meth
|
|
21
|
+
self.class.make_safe meth
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
def self.included(receiver)
|
|
26
|
+
receiver.extend MonitorMixin
|
|
27
|
+
receiver.extend ClassMethods
|
|
28
|
+
receiver.send :include, InstanceMethods
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
end
|