pogo 2.31.2
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/README.md +73 -0
- data/bin/pogo +22 -0
- data/data/cacert.pem +3988 -0
- data/lib/heroku.rb +22 -0
- data/lib/heroku/auth.rb +320 -0
- data/lib/heroku/cli.rb +38 -0
- data/lib/heroku/client.rb +764 -0
- data/lib/heroku/client/heroku_postgresql.rb +111 -0
- data/lib/heroku/client/pgbackups.rb +113 -0
- data/lib/heroku/client/rendezvous.rb +105 -0
- data/lib/heroku/client/ssl_endpoint.rb +25 -0
- data/lib/heroku/command.rb +273 -0
- data/lib/heroku/command/account.rb +23 -0
- data/lib/heroku/command/accounts.rb +34 -0
- data/lib/heroku/command/addons.rb +305 -0
- data/lib/heroku/command/apps.rb +311 -0
- data/lib/heroku/command/auth.rb +86 -0
- data/lib/heroku/command/base.rb +230 -0
- data/lib/heroku/command/certs.rb +148 -0
- data/lib/heroku/command/config.rb +137 -0
- data/lib/heroku/command/db.rb +218 -0
- data/lib/heroku/command/domains.rb +85 -0
- data/lib/heroku/command/drains.rb +46 -0
- data/lib/heroku/command/git.rb +65 -0
- data/lib/heroku/command/help.rb +163 -0
- data/lib/heroku/command/keys.rb +115 -0
- data/lib/heroku/command/labs.rb +161 -0
- data/lib/heroku/command/logs.rb +98 -0
- data/lib/heroku/command/maintenance.rb +61 -0
- data/lib/heroku/command/pg.rb +277 -0
- data/lib/heroku/command/pgbackups.rb +289 -0
- data/lib/heroku/command/plugins.rb +110 -0
- data/lib/heroku/command/ps.rb +232 -0
- data/lib/heroku/command/releases.rb +124 -0
- data/lib/heroku/command/run.rb +179 -0
- data/lib/heroku/command/sharing.rb +89 -0
- data/lib/heroku/command/ssl.rb +61 -0
- data/lib/heroku/command/stack.rb +62 -0
- data/lib/heroku/command/status.rb +51 -0
- data/lib/heroku/command/update.rb +47 -0
- data/lib/heroku/command/version.rb +23 -0
- data/lib/heroku/deprecated.rb +5 -0
- data/lib/heroku/deprecated/help.rb +38 -0
- data/lib/heroku/distribution.rb +9 -0
- data/lib/heroku/helpers.rb +517 -0
- data/lib/heroku/helpers/heroku_postgresql.rb +104 -0
- data/lib/heroku/plugin.rb +161 -0
- data/lib/heroku/updater.rb +158 -0
- data/lib/heroku/version.rb +3 -0
- data/lib/vendor/heroku/okjson.rb +598 -0
- data/spec/helper/legacy_help.rb +16 -0
- data/spec/heroku/auth_spec.rb +246 -0
- data/spec/heroku/client/heroku_postgresql_spec.rb +34 -0
- data/spec/heroku/client/pgbackups_spec.rb +43 -0
- data/spec/heroku/client/rendezvous_spec.rb +62 -0
- data/spec/heroku/client/ssl_endpoint_spec.rb +48 -0
- data/spec/heroku/client_spec.rb +564 -0
- data/spec/heroku/command/addons_spec.rb +585 -0
- data/spec/heroku/command/apps_spec.rb +351 -0
- data/spec/heroku/command/auth_spec.rb +38 -0
- data/spec/heroku/command/base_spec.rb +109 -0
- data/spec/heroku/command/certs_spec.rb +178 -0
- data/spec/heroku/command/config_spec.rb +144 -0
- data/spec/heroku/command/db_spec.rb +110 -0
- data/spec/heroku/command/domains_spec.rb +87 -0
- data/spec/heroku/command/drains_spec.rb +34 -0
- data/spec/heroku/command/git_spec.rb +116 -0
- data/spec/heroku/command/help_spec.rb +93 -0
- data/spec/heroku/command/keys_spec.rb +120 -0
- data/spec/heroku/command/labs_spec.rb +99 -0
- data/spec/heroku/command/logs_spec.rb +60 -0
- data/spec/heroku/command/maintenance_spec.rb +51 -0
- data/spec/heroku/command/pg_spec.rb +223 -0
- data/spec/heroku/command/pgbackups_spec.rb +280 -0
- data/spec/heroku/command/plugins_spec.rb +104 -0
- data/spec/heroku/command/ps_spec.rb +195 -0
- data/spec/heroku/command/releases_spec.rb +130 -0
- data/spec/heroku/command/run_spec.rb +86 -0
- data/spec/heroku/command/sharing_spec.rb +59 -0
- data/spec/heroku/command/ssl_spec.rb +32 -0
- data/spec/heroku/command/stack_spec.rb +46 -0
- data/spec/heroku/command/status_spec.rb +48 -0
- data/spec/heroku/command/version_spec.rb +16 -0
- data/spec/heroku/command_spec.rb +211 -0
- data/spec/heroku/helpers/heroku_postgresql_spec.rb +109 -0
- data/spec/heroku/helpers_spec.rb +48 -0
- data/spec/heroku/plugin_spec.rb +172 -0
- data/spec/heroku/updater_spec.rb +44 -0
- data/spec/spec.opts +1 -0
- data/spec/spec_helper.rb +209 -0
- data/spec/support/display_message_matcher.rb +49 -0
- data/spec/support/openssl_mock_helper.rb +8 -0
- metadata +220 -0
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
require "heroku/command/base"
|
|
2
|
+
|
|
3
|
+
# manage git for apps
|
|
4
|
+
#
|
|
5
|
+
class Heroku::Command::Git < Heroku::Command::Base
|
|
6
|
+
|
|
7
|
+
# git:clone [OPTIONS]
|
|
8
|
+
#
|
|
9
|
+
# clones an app repo
|
|
10
|
+
#
|
|
11
|
+
# if OPTIONS are specified they will be passed to git clone
|
|
12
|
+
#
|
|
13
|
+
# -n, --no-remote # don't create a git remote
|
|
14
|
+
# -r, --remote REMOTE # the git remote to create, default "heroku"
|
|
15
|
+
#
|
|
16
|
+
#Examples:
|
|
17
|
+
#
|
|
18
|
+
# $ heroku git:clone -a myapp
|
|
19
|
+
# Cloning into 'myapp'...
|
|
20
|
+
# Git remote heroku added
|
|
21
|
+
#
|
|
22
|
+
def clone
|
|
23
|
+
git_options = args.join(" ")
|
|
24
|
+
remote = options[:remote] || 'heroku'
|
|
25
|
+
|
|
26
|
+
app_data = api.get_app(app).body
|
|
27
|
+
|
|
28
|
+
display git("clone #{app_data['git_url']} #{git_options}")
|
|
29
|
+
|
|
30
|
+
unless $?.exitstatus > 0 || options[:no_remote].is_a?(FalseClass)
|
|
31
|
+
FileUtils.chdir(app_data['name']) do
|
|
32
|
+
create_git_remote(remote, app_data['git_url'])
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
# git:remote [OPTIONS]
|
|
38
|
+
#
|
|
39
|
+
# adds a git remote to an app repo
|
|
40
|
+
#
|
|
41
|
+
# if OPTIONS are specified they will be passed to git remote add
|
|
42
|
+
#
|
|
43
|
+
# -r, --remote REMOTE # the git remote to create, default "heroku"
|
|
44
|
+
#
|
|
45
|
+
#Examples:
|
|
46
|
+
#
|
|
47
|
+
# $ heroku git:remote -a myapp
|
|
48
|
+
# Git remote heroku added
|
|
49
|
+
#
|
|
50
|
+
# $ heroku git:remote -a myapp
|
|
51
|
+
# ! Git remote heroku already exists
|
|
52
|
+
#
|
|
53
|
+
def remote
|
|
54
|
+
git_options = args.join(" ")
|
|
55
|
+
remote = options[:remote] || 'heroku'
|
|
56
|
+
|
|
57
|
+
if git('remote').split("\n").include?(remote)
|
|
58
|
+
error("Git remote #{remote} already exists")
|
|
59
|
+
else
|
|
60
|
+
app_data = api.get_app(app).body
|
|
61
|
+
create_git_remote(remote, app_data['git_url'])
|
|
62
|
+
end
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
end
|
|
@@ -0,0 +1,163 @@
|
|
|
1
|
+
require "heroku/command/base"
|
|
2
|
+
require "heroku/deprecated/help"
|
|
3
|
+
|
|
4
|
+
# list commands and display help
|
|
5
|
+
#
|
|
6
|
+
class Heroku::Command::Help < Heroku::Command::Base
|
|
7
|
+
|
|
8
|
+
PRIMARY_NAMESPACES = %w( auth apps ps run addons config releases domains logs sharing )
|
|
9
|
+
|
|
10
|
+
include Heroku::Deprecated::Help
|
|
11
|
+
|
|
12
|
+
# help [COMMAND]
|
|
13
|
+
#
|
|
14
|
+
# list available commands or display help for a specific command
|
|
15
|
+
#
|
|
16
|
+
#Examples:
|
|
17
|
+
#
|
|
18
|
+
# $ heroku help
|
|
19
|
+
# Usage: heroku COMMAND [--app APP] [command-specific-options]
|
|
20
|
+
#
|
|
21
|
+
# Primary help topics, type "heroku help TOPIC" for more details:
|
|
22
|
+
#
|
|
23
|
+
# addons # manage addon resources
|
|
24
|
+
# apps # manage apps (create, destroy)
|
|
25
|
+
# ...
|
|
26
|
+
#
|
|
27
|
+
# Additional topics:
|
|
28
|
+
#
|
|
29
|
+
# account # manage heroku account options
|
|
30
|
+
# accounts # manage multiple heroku accounts
|
|
31
|
+
# ...
|
|
32
|
+
#
|
|
33
|
+
# $ heroku help apps:create
|
|
34
|
+
# Usage: heroku apps:create [NAME]
|
|
35
|
+
#
|
|
36
|
+
# create a new app
|
|
37
|
+
#
|
|
38
|
+
# --addons ADDONS # a comma-delimited list of addons to install
|
|
39
|
+
# -b, --buildpack BUILDPACK # a buildpack url to use for this app
|
|
40
|
+
# -r, --remote REMOTE # the git remote to create, default "heroku"
|
|
41
|
+
# -s, --stack STACK # the stack on which to create the app
|
|
42
|
+
#
|
|
43
|
+
def index
|
|
44
|
+
if command = args.shift
|
|
45
|
+
help_for_command(command)
|
|
46
|
+
else
|
|
47
|
+
help_for_root
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
alias_command "-h", "help"
|
|
52
|
+
alias_command "--help", "help"
|
|
53
|
+
|
|
54
|
+
private
|
|
55
|
+
|
|
56
|
+
def commands_for_namespace(name)
|
|
57
|
+
Heroku::Command.commands.values.select do |command|
|
|
58
|
+
command[:namespace] == name && command[:command] != name
|
|
59
|
+
end
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
def namespaces
|
|
63
|
+
namespaces = Heroku::Command.namespaces
|
|
64
|
+
namespaces.delete("app")
|
|
65
|
+
namespaces
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
def commands
|
|
69
|
+
Heroku::Command.commands
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
def legacy_help_for_namespace(namespace)
|
|
73
|
+
instance = Heroku::Command::Help.groups.map do |group|
|
|
74
|
+
[ group.title, group.select { |c| c.first =~ /^#{namespace}/ }.length ]
|
|
75
|
+
end.sort_by { |l| l.last }.last
|
|
76
|
+
return nil unless instance
|
|
77
|
+
return nil if instance.last.zero?
|
|
78
|
+
instance.first
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
def legacy_help_for_command(command)
|
|
82
|
+
Heroku::Command::Help.groups.each do |group|
|
|
83
|
+
group.each do |cmd, description|
|
|
84
|
+
return description if cmd.split(" ").first == command
|
|
85
|
+
end
|
|
86
|
+
end
|
|
87
|
+
nil
|
|
88
|
+
end
|
|
89
|
+
|
|
90
|
+
def primary_namespaces
|
|
91
|
+
PRIMARY_NAMESPACES.map { |name| namespaces[name] }.compact
|
|
92
|
+
end
|
|
93
|
+
|
|
94
|
+
def additional_namespaces
|
|
95
|
+
(namespaces.values - primary_namespaces)
|
|
96
|
+
end
|
|
97
|
+
|
|
98
|
+
def summary_for_namespaces(namespaces)
|
|
99
|
+
size = longest(namespaces.map { |n| n[:name] })
|
|
100
|
+
namespaces.sort_by {|namespace| namespace[:name]}.each do |namespace|
|
|
101
|
+
name = namespace[:name]
|
|
102
|
+
namespace[:description] ||= legacy_help_for_namespace(name)
|
|
103
|
+
puts " %-#{size}s # %s" % [ name, namespace[:description] ]
|
|
104
|
+
end
|
|
105
|
+
end
|
|
106
|
+
|
|
107
|
+
def help_for_root
|
|
108
|
+
puts "Usage: heroku COMMAND [--app APP] [command-specific-options]"
|
|
109
|
+
puts
|
|
110
|
+
puts "Primary help topics, type \"heroku help TOPIC\" for more details:"
|
|
111
|
+
puts
|
|
112
|
+
summary_for_namespaces(primary_namespaces)
|
|
113
|
+
puts
|
|
114
|
+
puts "Additional topics:"
|
|
115
|
+
puts
|
|
116
|
+
summary_for_namespaces(additional_namespaces)
|
|
117
|
+
puts
|
|
118
|
+
end
|
|
119
|
+
|
|
120
|
+
def help_for_namespace(name)
|
|
121
|
+
namespace_commands = commands_for_namespace(name)
|
|
122
|
+
|
|
123
|
+
unless namespace_commands.empty?
|
|
124
|
+
size = longest(namespace_commands.map { |c| c[:banner] })
|
|
125
|
+
namespace_commands.sort_by { |c| c[:banner].to_s }.each do |command|
|
|
126
|
+
next if command[:help] =~ /DEPRECATED/
|
|
127
|
+
command[:summary] ||= legacy_help_for_command(command[:command])
|
|
128
|
+
puts " %-#{size}s # %s" % [ command[:banner], command[:summary] ]
|
|
129
|
+
end
|
|
130
|
+
end
|
|
131
|
+
end
|
|
132
|
+
|
|
133
|
+
def help_for_command(name)
|
|
134
|
+
if command_alias = Heroku::Command.command_aliases[name]
|
|
135
|
+
display("Alias: #{name} redirects to #{command_alias}")
|
|
136
|
+
name = command_alias
|
|
137
|
+
end
|
|
138
|
+
if command = commands[name]
|
|
139
|
+
puts "Usage: heroku #{command[:banner]}"
|
|
140
|
+
|
|
141
|
+
if command[:help].strip.length > 0
|
|
142
|
+
puts command[:help].split("\n")[1..-1].join("\n")
|
|
143
|
+
else
|
|
144
|
+
puts
|
|
145
|
+
puts " " + legacy_help_for_command(name).to_s
|
|
146
|
+
end
|
|
147
|
+
puts
|
|
148
|
+
end
|
|
149
|
+
|
|
150
|
+
namespace_commands = commands_for_namespace(name).reject do |command|
|
|
151
|
+
command[:help] =~ /DEPRECATED/
|
|
152
|
+
end
|
|
153
|
+
|
|
154
|
+
if !namespace_commands.empty?
|
|
155
|
+
puts "Additional commands, type \"heroku help COMMAND\" for more details:"
|
|
156
|
+
puts
|
|
157
|
+
help_for_namespace(name)
|
|
158
|
+
puts
|
|
159
|
+
elsif command.nil?
|
|
160
|
+
error "#{name} is not a heroku command. See `heroku help`."
|
|
161
|
+
end
|
|
162
|
+
end
|
|
163
|
+
end
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
require "heroku/command/base"
|
|
2
|
+
|
|
3
|
+
module Heroku::Command
|
|
4
|
+
|
|
5
|
+
# manage authentication keys
|
|
6
|
+
#
|
|
7
|
+
class Keys < Base
|
|
8
|
+
|
|
9
|
+
# keys
|
|
10
|
+
#
|
|
11
|
+
# display keys for the current user
|
|
12
|
+
#
|
|
13
|
+
# -l, --long # display extended information for each key
|
|
14
|
+
#
|
|
15
|
+
#Examples:
|
|
16
|
+
#
|
|
17
|
+
# $ heroku keys
|
|
18
|
+
# === email@example.com Keys
|
|
19
|
+
# ssh-rsa ABCDEFGHIJK...OPQRSTUV== email@example.com
|
|
20
|
+
#
|
|
21
|
+
# $ heroku keys --long
|
|
22
|
+
# === email@example.com Keys
|
|
23
|
+
# ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEAp9AJD5QABmOcrkHm6SINuQkDefaR0MUrfgZ1Pxir3a4fM1fwa00dsUwbUaRuR7FEFD8n1E9WwDf8SwQTHtyZsJg09G9myNqUzkYXCmydN7oGr5IdVhRyv5ixcdiE0hj7dRnOJg2poSQ3Qi+Ka8SVJzF7nIw1YhuicHPSbNIFKi5s0D5a+nZb/E6MNGvhxoFCQX2IcNxaJMqhzy1ESwlixz45aT72mXYq0LIxTTpoTqma1HuKdRY8HxoREiivjmMQulYP+CxXFcMyV9kxTKIUZ/FXqlC6G5vSm3J4YScSatPOj9ID5HowpdlIx8F6y4p1/28r2tTl4CY40FFyoke4MQ== email@example.com
|
|
24
|
+
#
|
|
25
|
+
def index
|
|
26
|
+
validate_arguments!
|
|
27
|
+
keys = api.get_keys.body
|
|
28
|
+
if keys.length > 0
|
|
29
|
+
styled_header("#{Heroku::Auth.user} Keys")
|
|
30
|
+
keys = if options[:long]
|
|
31
|
+
keys.map {|key| key["contents"].strip}
|
|
32
|
+
else
|
|
33
|
+
keys.map {|key| format_key_for_display(key["contents"])}
|
|
34
|
+
end
|
|
35
|
+
styled_array(keys)
|
|
36
|
+
else
|
|
37
|
+
display("You have no keys.")
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
# keys:add [KEY]
|
|
42
|
+
#
|
|
43
|
+
# add a key for the current user
|
|
44
|
+
#
|
|
45
|
+
# if no KEY is specified, will try to find ~/.ssh/id_[rd]sa.pub
|
|
46
|
+
#
|
|
47
|
+
#Examples:
|
|
48
|
+
#
|
|
49
|
+
# $ heroku keys:add
|
|
50
|
+
# Could not find an existing public key.
|
|
51
|
+
# Would you like to generate one? [Yn] y
|
|
52
|
+
# Generating new SSH public key.
|
|
53
|
+
# Uploading SSH public key /.ssh/id_rsa.pub... done
|
|
54
|
+
#
|
|
55
|
+
# $ heroku keys:add /my/key.pub
|
|
56
|
+
# Uploading SSH public key /my/key.pub... done
|
|
57
|
+
#
|
|
58
|
+
def add
|
|
59
|
+
keyfile = shift_argument
|
|
60
|
+
validate_arguments!
|
|
61
|
+
|
|
62
|
+
if keyfile
|
|
63
|
+
Heroku::Auth.associate_key(keyfile)
|
|
64
|
+
else
|
|
65
|
+
# make sure we have credentials
|
|
66
|
+
Heroku::Auth.get_credentials
|
|
67
|
+
Heroku::Auth.associate_or_generate_ssh_key
|
|
68
|
+
end
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
# keys:remove KEY
|
|
72
|
+
#
|
|
73
|
+
# remove a key from the current user
|
|
74
|
+
#
|
|
75
|
+
#Examples:
|
|
76
|
+
#
|
|
77
|
+
# $ heroku keys:remove email@example.com
|
|
78
|
+
# Removing email@example.com SSH key... done
|
|
79
|
+
#
|
|
80
|
+
def remove
|
|
81
|
+
key = shift_argument
|
|
82
|
+
if key.nil? || key.empty?
|
|
83
|
+
error("Usage: heroku keys:remove KEY\nMust specify KEY to remove.")
|
|
84
|
+
end
|
|
85
|
+
validate_arguments!
|
|
86
|
+
|
|
87
|
+
action("Removing #{key} SSH key") do
|
|
88
|
+
api.delete_key(key)
|
|
89
|
+
end
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
# keys:clear
|
|
93
|
+
#
|
|
94
|
+
# remove all authentication keys from the current user
|
|
95
|
+
#
|
|
96
|
+
#Examples:
|
|
97
|
+
#
|
|
98
|
+
# $ heroku keys:cleare
|
|
99
|
+
# Removing all SSH keys... done
|
|
100
|
+
#
|
|
101
|
+
def clear
|
|
102
|
+
validate_arguments!
|
|
103
|
+
|
|
104
|
+
action("Removing all SSH keys") do
|
|
105
|
+
api.delete_keys
|
|
106
|
+
end
|
|
107
|
+
end
|
|
108
|
+
|
|
109
|
+
protected
|
|
110
|
+
def format_key_for_display(key)
|
|
111
|
+
type, hex, local = key.strip.split(/\s/)
|
|
112
|
+
[type, hex[0,10] + '...' + hex[-10,10], local].join(' ')
|
|
113
|
+
end
|
|
114
|
+
end
|
|
115
|
+
end
|
|
@@ -0,0 +1,161 @@
|
|
|
1
|
+
require "heroku/command/base"
|
|
2
|
+
|
|
3
|
+
# manage optional features
|
|
4
|
+
#
|
|
5
|
+
class Heroku::Command::Labs < Heroku::Command::Base
|
|
6
|
+
|
|
7
|
+
# labs [APP]
|
|
8
|
+
#
|
|
9
|
+
# lists enabled features for an app
|
|
10
|
+
#
|
|
11
|
+
#Example:
|
|
12
|
+
#
|
|
13
|
+
# $ heroku labs -a myapp
|
|
14
|
+
# === myapp Enabled Features
|
|
15
|
+
# sigterm-all: When stopping a dyno, send SIGTERM to all processes rather than only to the root process.
|
|
16
|
+
#
|
|
17
|
+
# === email@example.com Enabled Features
|
|
18
|
+
# sumo-rankings: Heroku Sumo ranks and visualizes the scale of your app, and suggests the optimum combination of dynos and add-ons to take it to the next level.
|
|
19
|
+
#
|
|
20
|
+
def index
|
|
21
|
+
validate_arguments!
|
|
22
|
+
|
|
23
|
+
if app
|
|
24
|
+
display_features(app, 'enabled', { 'enabled' => true, 'kind' => 'app' })
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
display_features(Heroku::Auth.user, 'enabled', { 'enabled' => true, 'kind' => 'user' })
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
# labs:info FEATURE
|
|
31
|
+
#
|
|
32
|
+
# displays additional information about FEATURE
|
|
33
|
+
#
|
|
34
|
+
#Example:
|
|
35
|
+
#
|
|
36
|
+
# $ heroku labs:info user_env_compile
|
|
37
|
+
# === user_env_compile
|
|
38
|
+
# Docs: http://devcenter.heroku.com/articles/labs-user-env-compile
|
|
39
|
+
# Summary: Add user config vars to the environment during slug compilation
|
|
40
|
+
#
|
|
41
|
+
def info
|
|
42
|
+
unless feature_name = shift_argument
|
|
43
|
+
error("Usage: heroku labs:info FEATURE\nMust specify FEATURE for info.")
|
|
44
|
+
end
|
|
45
|
+
validate_arguments!
|
|
46
|
+
|
|
47
|
+
feature_data = api.get_feature(feature_name, app).body
|
|
48
|
+
styled_header(feature_data['name'])
|
|
49
|
+
styled_hash({
|
|
50
|
+
'Summary' => feature_data['summary'],
|
|
51
|
+
'Docs' => feature_data['docs']
|
|
52
|
+
})
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
# labs:disable FEATURE
|
|
56
|
+
#
|
|
57
|
+
# disables FEATURE on an app
|
|
58
|
+
#
|
|
59
|
+
#Example:
|
|
60
|
+
#
|
|
61
|
+
# $ heroku labs:disable user_env_compile
|
|
62
|
+
# Disabling user_env_compile for myapp... done
|
|
63
|
+
#
|
|
64
|
+
def disable
|
|
65
|
+
unless feature_name = shift_argument
|
|
66
|
+
error("Usage: heroku labs:disable FEATURE\nMust specify FEATURE to disable.")
|
|
67
|
+
end
|
|
68
|
+
validate_arguments!
|
|
69
|
+
|
|
70
|
+
message = "Disabling #{feature_name}"
|
|
71
|
+
message += " for #{app}" if app
|
|
72
|
+
action(message) do
|
|
73
|
+
api.delete_feature(feature_name, app)
|
|
74
|
+
end
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
# labs:enable FEATURE
|
|
78
|
+
#
|
|
79
|
+
# enables FEATURE on an app
|
|
80
|
+
#
|
|
81
|
+
#Example:
|
|
82
|
+
#
|
|
83
|
+
# $ heroku labs:enable user_env_compile
|
|
84
|
+
# Enabling user_env_compile for myapp... done
|
|
85
|
+
# For more information see: http://devcenter.heroku.com/articles/labs-user-env-compile
|
|
86
|
+
#
|
|
87
|
+
def enable
|
|
88
|
+
unless feature_name = shift_argument
|
|
89
|
+
error("Usage: heroku labs:enable FEATURE\nMust specify FEATURE to enable.")
|
|
90
|
+
end
|
|
91
|
+
validate_arguments!
|
|
92
|
+
|
|
93
|
+
message = "Enabling #{feature_name}"
|
|
94
|
+
message += " for #{app}" if app
|
|
95
|
+
feature_data = nil
|
|
96
|
+
action(message) do
|
|
97
|
+
feature_data = api.post_feature(feature_name, app).body
|
|
98
|
+
end
|
|
99
|
+
display("WARNING: This feature is experimental and may change or be removed without notice.")
|
|
100
|
+
display("For more information see: #{feature_data['docs']}")
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
# labs:list
|
|
104
|
+
#
|
|
105
|
+
# lists available features
|
|
106
|
+
#
|
|
107
|
+
#Example:
|
|
108
|
+
#
|
|
109
|
+
# $ heroku labs:list
|
|
110
|
+
# === App Available Features
|
|
111
|
+
# dot-profile: Source .profile during dyno startup
|
|
112
|
+
# preboot: Provide seamless deploys by booting web dynos with new code before killing existing web dynos.
|
|
113
|
+
# user_env_compile: Add user config vars to the environment during slug compilation
|
|
114
|
+
#
|
|
115
|
+
# === User Available Features
|
|
116
|
+
# default-heroku-postgresql-dev: Use the new heroku-postgresql:dev add-on as the default database for Cedar apps.
|
|
117
|
+
#
|
|
118
|
+
def list
|
|
119
|
+
validate_arguments!
|
|
120
|
+
|
|
121
|
+
display_features('App', 'available', { 'kind' => 'app' })
|
|
122
|
+
display_features('User', 'available', { 'kind' => 'user' })
|
|
123
|
+
end
|
|
124
|
+
|
|
125
|
+
private
|
|
126
|
+
|
|
127
|
+
def app
|
|
128
|
+
# app is not required for these commands, so rescue if there is none
|
|
129
|
+
super
|
|
130
|
+
rescue Heroku::Command::CommandFailed
|
|
131
|
+
nil
|
|
132
|
+
end
|
|
133
|
+
|
|
134
|
+
def display_features(type, status, attributes)
|
|
135
|
+
@features ||= api.get_features(app).body
|
|
136
|
+
|
|
137
|
+
selected_features = @features.dup
|
|
138
|
+
attributes.each do |key, value|
|
|
139
|
+
selected_features = selected_features.select {|feature| feature[key] == value}
|
|
140
|
+
end
|
|
141
|
+
|
|
142
|
+
feature_hash = {}
|
|
143
|
+
selected_features.each do |feature|
|
|
144
|
+
feature_hash[feature['name']] = feature['summary']
|
|
145
|
+
end
|
|
146
|
+
|
|
147
|
+
if feature_hash.empty?
|
|
148
|
+
case status
|
|
149
|
+
when 'available'
|
|
150
|
+
display("There are no #{type} features available.")
|
|
151
|
+
when 'enabled'
|
|
152
|
+
display("#{type} has no enabled features.")
|
|
153
|
+
end
|
|
154
|
+
else
|
|
155
|
+
styled_header("#{type} #{status.capitalize} Features")
|
|
156
|
+
styled_hash(feature_hash)
|
|
157
|
+
display
|
|
158
|
+
end
|
|
159
|
+
end
|
|
160
|
+
|
|
161
|
+
end
|