tannins 0.6

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1 @@
1
+ pkg
@@ -0,0 +1,6 @@
1
+ [submodule "spec/rails"]
2
+ path = spec/rails
3
+ url = git@github.com:notch8/tannins-rails-fixture.git
4
+ [submodule "spec/merb"]
5
+ path = spec/merb
6
+ url = git@github.com:notch8/tannins-merb-fixture.git
@@ -0,0 +1,3 @@
1
+ == 0.1.0 / 2008-08-21
2
+
3
+ * First public release
@@ -0,0 +1,87 @@
1
+ tannins
2
+ by FIXME (your name)
3
+ FIXME (url)
4
+
5
+ == DESCRIPTION:
6
+
7
+ Variables:
8
+
9
+ user
10
+ group
11
+ use_nginx
12
+ application
13
+ mongrel_servers
14
+ precedence
15
+ server_name
16
+ ssl_required
17
+ forced_prefix
18
+
19
+ database_adapter
20
+ database_username
21
+ database_password
22
+ database_host # optional
23
+ database_socket # optional
24
+
25
+ === EC2 SPECIFIC VARIABLES
26
+
27
+ ec2_access_key
28
+ ec2_secret_key
29
+ ec2_ami_image
30
+ ec2_elastic_ip
31
+
32
+ == DEPLOY SPECIFIC VARIABLES
33
+
34
+ deploy_username
35
+ deploy_password
36
+
37
+ == APPLICATION SPECIFIC VARIABLES
38
+
39
+ github_sshkey
40
+ mysql_password
41
+
42
+ == BACKUP SPECIFIC VARIABLES
43
+
44
+ s3_id
45
+ s3_key
46
+ s3_backup_bucket
47
+
48
+ == FEATURES/PROBLEMS:
49
+
50
+ * FIXME (list of features or problems)
51
+
52
+ == SYNOPSIS:
53
+
54
+ FIXME (code sample of usage)
55
+
56
+ == REQUIREMENTS:
57
+
58
+ * FIXME (list of requirements)
59
+
60
+ == INSTALL:
61
+
62
+ * FIXME (sudo gem install, anything else)
63
+
64
+ == LICENSE:
65
+
66
+ (The MIT License)
67
+
68
+ Copyright (c) 2008 FIXME (different license?)
69
+
70
+ Permission is hereby granted, free of charge, to any person obtaining
71
+ a copy of this software and associated documentation files (the
72
+ 'Software'), to deal in the Software without restriction, including
73
+ without limitation the rights to use, copy, modify, merge, publish,
74
+ distribute, sublicense, and/or sell copies of the Software, and to
75
+ permit persons to whom the Software is furnished to do so, subject to
76
+ the following conditions:
77
+
78
+ The above copyright notice and this permission notice shall be
79
+ included in all copies or substantial portions of the Software.
80
+
81
+ THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND,
82
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
83
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
84
+ IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
85
+ CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
86
+ TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
87
+ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,23 @@
1
+ # Look in the tasks/setup.rb file for the various options that can be
2
+ # configured in this Rakefile. The .rake files in the tasks directory
3
+ # are where the options are used.
4
+
5
+ load 'tasks/setup.rb'
6
+
7
+ ensure_in_path 'lib'
8
+ require 'tannins'
9
+
10
+ task :default => 'spec:run'
11
+
12
+ PROJ.name = 'tannins'
13
+ PROJ.authors = 'Rob Kaufman, Chris Petersen and Ryan Felton'
14
+ PROJ.email = 'rob@notch8.com'
15
+ PROJ.url = 'http://notch8.com'
16
+ PROJ.rubyforge.name = 'tannins'
17
+ PROJ.version = Tannins::VERSION
18
+ PROJ.spec.opts << '--color'
19
+ PROJ.ignore_file = '.bnsignore'
20
+ depend_on 'amazon-ec2'
21
+ depend_on 'mongrel_cluster'
22
+
23
+ # EOF
@@ -0,0 +1,64 @@
1
+ # $Id$
2
+ # Equivalent to a header guard in C/C++
3
+ # Used to prevent the class/module from being loaded more than once
4
+ unless defined? Tannins
5
+
6
+ module Tannins
7
+
8
+ # :stopdoc:
9
+ VERSION = '0.6'
10
+ LIBPATH = ::File.expand_path(::File.dirname(__FILE__)) + ::File::SEPARATOR
11
+ PATH = ::File.dirname(LIBPATH) + ::File::SEPARATOR
12
+ # :startdoc:
13
+
14
+ def self.get_template(file_name)
15
+ file_path = File.join(Dir.pwd, "config", "templates", file_name)
16
+ if File.exists?(file_path)
17
+ return file_path
18
+ else
19
+ return "#{File.expand_path(File.dirname(__FILE__))}/templates"
20
+ end
21
+ end
22
+
23
+ # Returns the version string for the library.
24
+ #
25
+ def self.version
26
+ VERSION
27
+ end
28
+
29
+ # Returns the library path for the module. If any arguments are given,
30
+ # they will be joined to the end of the libray path using
31
+ # <tt>File.join</tt>.
32
+ #
33
+ def self.libpath( *args )
34
+ args.empty? ? LIBPATH : ::File.join(LIBPATH, *args)
35
+ end
36
+
37
+ # Returns the lpath for the module. If any arguments are given,
38
+ # they will be joined to the end of the path using
39
+ # <tt>File.join</tt>.
40
+ #
41
+ def self.path( *args )
42
+ args.empty? ? PATH : ::File.join(PATH, *args)
43
+ end
44
+
45
+ # Utility method used to rquire all files ending in .rb that lie in the
46
+ # directory below this file that has the same name as the filename passed
47
+ # in. Optionally, a specific _directory_ name can be passed in such that
48
+ # the _filename_ does not have to be equivalent to the directory.
49
+ #
50
+ def self.require_all_libs_relative_to( fname, dir = nil )
51
+ dir ||= ::File.basename(fname, '.*')
52
+ search_me = ::File.expand_path(
53
+ ::File.join(::File.dirname(fname), dir, '**', '*.rb'))
54
+
55
+ Dir.glob(search_me).sort.each {|rb| require rb}
56
+ end
57
+
58
+ end # module Tannins
59
+
60
+ # Tannins.require_all_libs_relative_to __FILE__
61
+
62
+ end # unless defined?
63
+
64
+ # EOF
@@ -0,0 +1,27 @@
1
+ require 'erubis'
2
+ Capistrano::Configuration.instance(:must_exist).load do
3
+ namespace :gentoo do
4
+ desc "Setup Apache Configuration"
5
+ task :web_configuration_setup, :roles => :web do
6
+ sudo "mkdir -p /etc/apache2/vhosts.d"
7
+
8
+ vhost_file = Tannins.get_template("apache_vhost.erb")
9
+ common_file = Tannins.get_template("apache_common.erb")
10
+
11
+ # generate web server configuration (apache specific)
12
+ apache2_rails_conf = ::Erubis::Eruby.new(File.read(vhost_file)).result(binding)
13
+
14
+ apache2_rails_common_conf = ::Erubis::Eruby.new(File.read(common_file)).result(binding)
15
+
16
+ put apache2_rails_conf, "#{shared_path}/system/#{application}.conf"
17
+ put apache2_rails_common_conf, "#{shared_path}/system/#{application}.common"
18
+
19
+ # if apache is setup to read /etc/apache2/vhosts.d/*.conf these will get read as configuration files
20
+ # see prerequisites above for more info
21
+ sudo "ln -nfs #{shared_path}/config/#{application}.conf /etc/apache2/vhosts.d/#{precedence}_#{application}.conf"
22
+ sudo "ln -nfs #{shared_path}/config/#{application}.common /etc/apache2/vhosts.d/#{application}.common"
23
+ sudo "rc-update add apache2 default"
24
+
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,123 @@
1
+ require 'EC2'
2
+ require 'erubis'
3
+
4
+ Capistrano::Configuration.instance(:must_exist).load do
5
+ namespace :ec2 do
6
+ desc 'Creates a new EC2 instance and runs then launch_new.rb script'
7
+ task :new do
8
+ LIBPATH = ::File.expand_path(::File.dirname(__FILE__)) + ::File::SEPARATOR
9
+
10
+ if File.exists?( "#{Dir.pwd}/config/ec2/launch_new.rb" )
11
+ user_data = File.read( "#{Dir.pwd}/config/ec2/launch_new.rb" )
12
+ else
13
+ user_data = ""
14
+ end
15
+ # user_data += File.read( "#{LIBPATH}launch_new.erb" )
16
+
17
+ processed_erb = ::Erubis::Eruby.new(File.read("#{LIBPATH}templates/launch_new.erb")).result(binding)
18
+ # raw_erb = File.read( "#{LIBPATH}launch_new.erb" )
19
+ # processed_erb = ERB.new( raw_erb )
20
+ user_data += processed_erb
21
+
22
+ ec2 = EC2::Base.new(:access_key_id => ec2_access_key, :secret_access_key => ec2_secret_key)
23
+ reservation = ec2.run_instances(:image_id => ec2_ami_image,
24
+ :keypair => "#{Dir.pwd}/config/ec2/id_rsa-gsg-keypair",
25
+ :instance_type => "m1.small",
26
+ :user_data => user_data)
27
+
28
+ reservation.instancesSet.item.each do |item|
29
+ raise Exception, "Instance did not start." unless item.instanceState.name == "pending"
30
+ puts "Instance #{item.instanceId} Startup Pending"
31
+ puts "Checking every 10 seconds to detect startup for up to 5 minutes"
32
+ tries = 0
33
+ while tries < 35
34
+ launched = ec2.describe_instances(:instance_id =>[item.instanceId]).reservationSet.item.first.instancesSet.item.first
35
+ case launched.instanceState.name
36
+ when "pending"
37
+ print '.'
38
+ $stdout.flush
39
+ sleep 10
40
+ tries += 1
41
+ when "running"
42
+ puts "running #{item.instanceId} at #{launched.dnsName}"
43
+ assign_ip(ec2, item.instanceId)
44
+ break
45
+ else
46
+ puts "error initializing instance: #{item.instanceId}"
47
+ break
48
+ end
49
+ end
50
+ end
51
+
52
+ end
53
+
54
+ desc 'Shuts down an instance'
55
+ task :terminate do
56
+ raise "INSTANCE_ID required" unless instance_id = ENV['INSTANCE_ID']
57
+
58
+ ec2 = EC2::Base.new(:access_key_id => ec2_access_key, :secret_access_key => ec2_secret_key)
59
+ ec2.terminate_instances(:instance_id => [instance_id])
60
+ end
61
+
62
+ desc 'Returns all of your currently running instances'
63
+ task :instances do
64
+ ec2 = EC2::Base.new(:access_key_id => ec2_access_key, :secret_access_key => ec2_secret_key)
65
+ ec2.describe_instances.reservationSet.item.each do |set|
66
+ set.instancesSet.item.each do |instance|
67
+ str = instance.instanceId
68
+ str << " ("
69
+ str << instance.instanceState.name
70
+ if instance.instanceState.name == "running"
71
+ str << " at "
72
+ str << instance.dnsName
73
+ str << " on image "
74
+ str << instance.imageId
75
+ str << " launched at "
76
+ str << instance.launchTime
77
+ end
78
+ str << ")"
79
+ puts str
80
+ end
81
+ end
82
+ end
83
+
84
+ desc "return your own amazon images."
85
+ task :images do
86
+ ec2 = EC2::Base.new(:access_key_id => ec2_access_key, :secret_access_key => ec2_secret_key)
87
+ ec2.describe_images(:owner_id => "self").imagesSet.item.each do |image|
88
+ str = image.imageId
89
+ str << " ("
90
+ str << image.imageLocation
91
+ str << ") status: ("
92
+ str <<
93
+ str << image.imageState
94
+ str << " and "
95
+ p = (image.isPublic == "true")? "public" : "private"
96
+ str << p
97
+ str << ")"
98
+ puts str
99
+ end
100
+ end
101
+
102
+ desc "change the production/staging ip to the value of INSTANCE_ID. stagings is used unless RAILS_ENV=production"
103
+ task :assign_ip do
104
+ raise "INSTANCE_ID required" unless ENV['INSTANCE_ID']
105
+ ec2 = EC2::Base.new(:access_key_id => ec2_access_key, :secret_access_key => ec2_secret_key)
106
+ assign_ip(ec2, ENV['INSTANCE_ID'], true)
107
+ end
108
+
109
+ def assign_ip(ec2, instance_id, force = false)
110
+ environment_var = ENV['RAILS_ENV'] || ENV['MERB_ENV']
111
+ if environment_var == 'production' && force
112
+ puts "Changing where the PRODUCTIOIN IP address points"
113
+ ec2.associate_address(:instance_id => instance_id, :public_ip => PRODUCTION_IP)
114
+ elsif ENV['RAILS_ENV'] == 'production'
115
+ puts "We don't move the production elastic IP automatically..."
116
+ puts "you have to force it by doing 'rake ec2:assign_ip INSTANCE_ID=#{instance_id} RAILS_ENV=production"
117
+ else
118
+ puts "Changing where the IP address points"
119
+ ec2.associate_address(:instance_id => instance_id, :public_ip => ec2_elastic_ip)
120
+ end
121
+ end
122
+ end
123
+ end
@@ -0,0 +1,21 @@
1
+ Capistrano::Configuration.instance(:must_exist).load do
2
+ namespace :deploy do
3
+ desc 'restart mongrel cluster'
4
+ task :restart do
5
+ run "cd #{current_release} && mongrel_rails cluster::restart"
6
+ end
7
+
8
+ task :start do
9
+ run "cd #{current_release} && mongrel_rails cluster::start"
10
+ end
11
+
12
+ task :stop do
13
+ run "cd #{current_release} && mongrel_rails cluster::stop"
14
+ end
15
+
16
+ desc 'rails cluster status'
17
+ task :cluster_status do
18
+ run "cd #{current_release} && mongrel_rails cluster::status"
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,100 @@
1
+ require 'erubis'
2
+ Capistrano::Configuration.instance(:must_exist).load do
3
+ after 'deploy:update_code', 'deploy:symlink_configs'
4
+
5
+ before 'deploy:setup', 'gentoo:set_keys'
6
+ after 'deploy:setup', 'gentoo:fix_permissions'
7
+ after 'deploy:setup', 'deploy:update'
8
+ after 'deploy:setup', 'gentoo:setup'
9
+
10
+ namespace :tannins do
11
+ desc "Copy templates over for editing"
12
+ task :copy_templates do
13
+ run_locally "mkdir -p config/templates"
14
+ run_locally "cp -r #{Tannins.path}/lib/tannins/templates/* config/templates/"
15
+ end
16
+
17
+ desc "Show which template would be used for TEMPLATE"
18
+ task :template do
19
+ puts Tannins.get_template(ENV["TEMPLATE"])
20
+ end
21
+ end
22
+
23
+ namespace :gentoo do
24
+ # =============================================================================
25
+ # CALLBACK TASKS
26
+ # =============================================================================
27
+
28
+ desc "Tasks to execute before initial setup"
29
+ task :fix_permissions do
30
+ sudo "mkdir -p /etc/mongrel_cluster"
31
+
32
+ sudo "chown -R #{user}:#{group} #{deploy_to}"
33
+ # make shared config dir to hold these config files
34
+ run "mkdir -p #{shared_path}/config"
35
+
36
+ # make a shared tmp dir for sessions
37
+ run "mkdir -p #{shared_path}/tmp"
38
+ run "mkdir -p #{shared_path}/tmp/cache"
39
+ run "mkdir -p #{shared_path}/tmp/sessions"
40
+ run "mkdir -p #{shared_path}/tmp/sockets"
41
+ # run "mkdir -p #{shared_path}/tmp/pids" # new rails construct
42
+ # create any other shared dirs
43
+ # run "mkdir -p #{shared_path}/db"
44
+ # run "mkdir -p #{shared_path}/db/ferret_index"
45
+ end
46
+
47
+ before 'gentoo:setup', 'gentoo:application_configuration_setup'
48
+ before 'gentoo:setup', 'gentoo:database_configuration_setup'
49
+ before 'gentoo:setup', 'gentoo:web_configuration_setup'
50
+
51
+ desc "Tasks to execute after initial setup"
52
+ task :setup do
53
+ rake = fetch(:rake, "rake")
54
+ run "cd #{latest_release} && #{rake} db:create db:migrate RAILS_ENV=#{rails_env}"
55
+ end
56
+
57
+ desc "Setup Database Configuration"
58
+ task :database_configuration_setup do
59
+ # generate database configuration
60
+ database_file = Tannins.get_template("database.erb")
61
+ database_conf = Erubis::Eruby.new(File.read(database_file)).result(binding)
62
+
63
+ # put database configuration in shared config dir
64
+ put database_conf, "#{shared_path}/config/database.yml"
65
+ end
66
+
67
+ desc "Add the deploy keys to the deployment user"
68
+ task :set_keys, :roles => :app do
69
+ sudo "mkdir -p #{deploy_to}"
70
+ sudo "chown -R #{user}:#{group} #{deploy_to}"
71
+
72
+ key_file = File.read("#{Dir.pwd}/config/deploy_key")
73
+ pub_file = File.read("#{Dir.pwd}/config/deploy_key.pub")
74
+ run "mkdir -p /home/#{user}/.ssh/"
75
+ put key_file, "/home/#{user}/.ssh/id_dsa"
76
+ put pub_file, "/home/#{user}/.ssh/id_dsa.pub"
77
+ sudo "chmod 600 /home/#{user}/.ssh/id_dsa"
78
+ end
79
+ end
80
+
81
+ task :testing do
82
+ puts fetch(:database_host, "")
83
+ end
84
+
85
+
86
+ namespace :deploy do
87
+
88
+ desc "Symlinks the database and mongrel cluster configs"
89
+ task :symlink_configs, :roles => [:web] do
90
+ symlink_database_config
91
+ end
92
+
93
+ desc "Link to the shared database.yml."
94
+ task :symlink_database_config, :roles => [:web] do
95
+ run "rm -f #{latest_release}/config/database.yml"
96
+ run "ln -nfs #{shared_path}/config/database.yml #{latest_release}/config/database.yml"
97
+ end
98
+ end
99
+
100
+ end