bbcloud 0.9.2 → 0.10.1

Sign up to get free protection for your applications and to get access to all the features.
data/README CHANGED
@@ -35,7 +35,7 @@ branch.
35
35
 
36
36
  == License
37
37
 
38
- Copyright (c) 2010 John Leach, Brightbox Systems Ltd <john@brightbox.co.uk>
38
+ Copyright (c) 2010,2011 John Leach, Brightbox Systems Ltd <john@brightbox.co.uk>
39
39
 
40
40
  Permission is hereby granted, free of charge, to any person obtaining a copy
41
41
  of this software and associated documentation files (the "Software"), to deal
data/README.rdoc CHANGED
@@ -35,7 +35,7 @@ branch.
35
35
 
36
36
  == License
37
37
 
38
- Copyright (c) 2010 John Leach, Brightbox Systems Ltd <john@brightbox.co.uk>
38
+ Copyright (c) 2010,2011 John Leach, Brightbox Systems Ltd <john@brightbox.co.uk>
39
39
 
40
40
  Permission is hereby granted, free of charge, to any person obtaining a copy
41
41
  of this software and associated documentation files (the "Software"), to deal
data/bbcloud.gemspec CHANGED
@@ -23,10 +23,10 @@ Gem::Specification.new do |s|
23
23
  s.add_dependency 'json', '=1.4.6'
24
24
  s.add_dependency 'json_pure', '=1.4.6'
25
25
 
26
- s.add_dependency 'gli', '1.1.2'
26
+ s.add_dependency 'gli', '1.2.5'
27
27
  s.add_dependency 'hirb', '0.3.5'
28
- s.add_dependency 'fog', '=0.3.23'
29
- s.add_dependency 'excon', '>=0.2.4'
28
+ s.add_dependency 'fog', '=0.4.0'
29
+ s.add_dependency 'excon', '>=0.3.7'
30
30
  s.add_dependency 'ini', '0.1.1'
31
31
 
32
32
  end
data/bin/brightbox-lbs ADDED
@@ -0,0 +1,9 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ begin
4
+ require "bbcloud/cli"
5
+ rescue LoadError
6
+ bbcloud_path = File.expand_path('../../lib', __FILE__)
7
+ $:.unshift(bbcloud_path)
8
+ require "bbcloud/cli"
9
+ end
data/lib/bbcloud/cli.rb CHANGED
@@ -5,7 +5,7 @@ unless defined?(DISABLE_RUBYGEMS)
5
5
  require "rubygems"
6
6
  gem "json", "=1.4.6"
7
7
  gem "json_pure", "=1.4.6"
8
- gem "fog", "=0.3.23"
8
+ gem "fog", "=0.4.0"
9
9
  end
10
10
 
11
11
  # Add any vendored libraries into search path
@@ -44,7 +44,7 @@ module Fog
44
44
  end
45
45
  end
46
46
 
47
- %w{api servers images types zones cloud_ips users accounts config version}.each do |f|
47
+ %w{api servers images types zones cloud_ips users accounts config version load_balancers}.each do |f|
48
48
  require File.join(File.dirname(__FILE__), f)
49
49
  end
50
50
 
@@ -18,7 +18,13 @@ module Brightbox
18
18
  end
19
19
 
20
20
  def attributes
21
- fog_model.attributes
21
+ a = fog_model.attributes
22
+ if a["load_balancer"]
23
+ a[:destination] = a["load_balancer"]["id"]
24
+ else
25
+ a[:destination] = a[:server_id]
26
+ end
27
+ a
22
28
  end
23
29
 
24
30
  def to_row
@@ -30,7 +36,7 @@ module Brightbox
30
36
  end
31
37
 
32
38
  def self.default_field_order
33
- [:id, :status, :public_ip, :server_id, :interface_id, :reverse_dns]
39
+ [:id, :status, :public_ip, :destination, :reverse_dns]
34
40
  end
35
41
 
36
42
  def <=>(b)
@@ -1,5 +1,5 @@
1
1
  desc 'map Cloud IPs'
2
- arg_name 'cloudip-id server-id'
2
+ arg_name 'cloudip-id destination'
3
3
  command [:map] do |c|
4
4
  c.desc "Unmap mapped ips before remapping them"
5
5
  c.switch [:u, "unmap"]
@@ -11,16 +11,28 @@ command [:map] do |c|
11
11
  end
12
12
 
13
13
  if args.size < 2
14
- raise "You must specify the cloud ip id and the server id"
14
+ raise "You must specify the cloud ip id and the destination"
15
15
  end
16
16
 
17
17
  ip_id = args.first
18
18
 
19
19
  ip = CloudIP.find ip_id
20
20
 
21
+ destination_id = args.last
22
+ case destination_id
23
+ when /^srv\-/
24
+ server = Server.find destination_id
25
+ destination_id = server.interfaces.first["id"]
26
+ info "Mapping #{ip} to interface #{destination_id} on #{server}"
27
+ when /^lba\-/
28
+ lb = LoadBalancer.find destination_id
29
+ info "Mapping #{ip} to load balancer #{lb}"
30
+ else
31
+ raise "Unknown destination '#{destination_id}'"
32
+ end
33
+
21
34
  if ip.mapped?
22
35
  if options[:u]
23
- info "Unmapping ip #{ip}"
24
36
  ip.unmap
25
37
  3.times do
26
38
  break unless ip.mapped?
@@ -32,13 +44,7 @@ command [:map] do |c|
32
44
  end
33
45
  end
34
46
 
35
- server_id = args.last
36
- server = Server.find server_id
37
-
38
- interface_id = server.interfaces.first["id"]
39
- info "Mapping #{ip} to interface #{interface_id} on #{server}"
40
-
41
- ip.map interface_id
47
+ ip.map destination_id
42
48
 
43
49
  # Wait up to 3 seconds for mapping to complete
44
50
  3.times do
@@ -12,7 +12,7 @@ command [:show] do |c|
12
12
  warn "Couldn't find cloud ip #{id}"
13
13
  end
14
14
 
15
- fields = [:id, :status, :public_ip, :reverse_dns, :server_id, :interface_id]
15
+ fields = [:id, :status, :public_ip, :reverse_dns, :destination, :interface_id]
16
16
 
17
17
  render_table(ips.compact, global_options.merge({ :vertical => true, :fields => fields}))
18
18
  end
@@ -0,0 +1,20 @@
1
+ desc 'Add nodes to a load balancer'
2
+ arg_name 'lb-id node-id...'
3
+ command [:add_nodes] do |c|
4
+
5
+ c.action do |global_options, options, args|
6
+
7
+ raise "You must specify the load balancer and the node ids to add" if args.size < 2
8
+
9
+ lb = LoadBalancer.find(args.shift)
10
+
11
+ nodes = Server.find_or_call(args) do |id|
12
+ raise "Couldn't find server #{id}"
13
+ end
14
+
15
+ info "Adding #{nodes.size} nodes to load balancer #{lb.id}"
16
+ lb.add_nodes nodes
17
+ lb.reload
18
+ render_table([lb], global_options)
19
+ end
20
+ end
@@ -0,0 +1,87 @@
1
+ desc 'Create a load balancer'
2
+ long_desc "All intervals and timeouts are in milliseconds"
3
+ arg_name 'srv-id...'
4
+ command [:create] do |c|
5
+
6
+ c.desc "Friendly name of load balancer"
7
+ c.flag [:n, :name]
8
+
9
+ c.desc "Load balancer policy"
10
+ c.default_value "least-connections"
11
+ c.flag [:p, :policy]
12
+
13
+ c.desc "Listeners. Format: in-port:out-port:type. Comma separate multiple listeners."
14
+ c.default_value "80:80:http,443:443:tcp"
15
+ c.flag [:l, :listeners]
16
+
17
+ c.desc "Healthcheck port. Defaults to first listener out port."
18
+ c.flag [:k, "hc-port"]
19
+
20
+ c.desc "Healthcheck type. Defaults to first listener protocol."
21
+ c.flag [:y, "hc-type"]
22
+
23
+ c.desc "Healthcheck timeout"
24
+ c.default_value "5000"
25
+ c.flag [:t, "hc-timeout"]
26
+
27
+ c.desc "Healthcheck request. When the type is 'http' this is the url to request."
28
+ c.default_value "/"
29
+ c.flag [:s, "hc-request"]
30
+
31
+ c.desc "Healthcheck interval"
32
+ c.default_value "5000"
33
+ c.flag [:e, "hc-interval"]
34
+
35
+ c.desc "Healthcheck threshold up. Number of successful healthchecks for the node to be considered up."
36
+ c.default_value "3"
37
+ c.flag [:u, "hc-up"]
38
+
39
+ c.desc "Healthcheck threshold down. Number of failed healthchecks for the node to be considered down."
40
+ c.default_value "3"
41
+ c.flag [:d, "hc-down"]
42
+
43
+ c.action do |global_options, options, args|
44
+
45
+ raise "You must specify which servers to balance connections to" if args.empty?
46
+
47
+ listeners = options[:l].split(",").collect do |l|
48
+ inport, outport, protocol = l.split ":"
49
+ raise "listener '#{l}' is invalid" if inport.nil? or outport.nil? or protocol.nil?
50
+ { :in => inport, :out => outport, :protocol => protocol }
51
+ end
52
+
53
+ raise "You must specify at least one listener" if listeners.empty?
54
+
55
+ # Setup default healthcheck port if not specified
56
+ if options[:k].nil?
57
+ options[:k] = listeners.first[:out]
58
+ end
59
+
60
+ if options[:y].nil?
61
+ options[:y] = listeners.first[:protocol]
62
+ end
63
+
64
+ hc_arg_lookup = { :k => :port, :y => :type, :t => :timeout, :s =>
65
+ :request, :e => :interval, :u => :threshold_up, :d =>
66
+ :threshold_down }
67
+
68
+ healthcheck = {}
69
+
70
+ options.keys.each do |k|
71
+ if options[k] and hc_arg_lookup[k]
72
+ healthcheck[hc_arg_lookup[k]] = options[k]
73
+ end
74
+ end
75
+
76
+ nodes = args.collect { |i| { :node => i } }
77
+
78
+ msg = "Creating a new load balancer"
79
+ info msg
80
+ lb = LoadBalancer.create(:policy => options[:policy],
81
+ :name => options[:n],
82
+ :healthcheck => healthcheck,
83
+ :listeners => listeners,
84
+ :nodes => nodes)
85
+ render_table([lb], global_options)
86
+ end
87
+ end
@@ -0,0 +1,18 @@
1
+ desc 'Destroy load balancers'
2
+ arg_name 'lb-id...'
3
+ command [:destroy] do |c|
4
+
5
+ c.action do |global_options, options, args|
6
+
7
+ raise "You must specify the load balancers to destroy" if args.empty?
8
+
9
+ lbs = LoadBalancer.find_or_call(args) do |id|
10
+ raise "Couldn't find load balancer #{id}"
11
+ end
12
+
13
+ lbs.each do |lb|
14
+ info "Destroying load balancer #{lb}"
15
+ lb.destroy
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,16 @@
1
+ desc 'List load balancers'
2
+ arg_name '[lb-id...]'
3
+ command [:list] do |c|
4
+ c.action do |global_options,options,args|
5
+
6
+ if args.empty?
7
+ lbs = LoadBalancer.find(:all)
8
+ else
9
+ lbs = LoadBalancer.find_or_call(args) do |id|
10
+ warn "Couldn't find load balancer #{id}"
11
+ end
12
+ end
13
+
14
+ render_table(lbs, global_options)
15
+ end
16
+ end
@@ -0,0 +1,20 @@
1
+ desc 'Remove nodes from a load balancer'
2
+ arg_name 'lb-id node-id...'
3
+ command [:remove_nodes] do |c|
4
+
5
+ c.action do |global_options, options, args|
6
+
7
+ raise "You must specify the load balancer and the node ids to remove" if args.size < 2
8
+
9
+ lb = LoadBalancer.find(args.shift)
10
+
11
+ # We don't want to check servers exist as you can remove deleted
12
+ # servers from a load balancer.
13
+ nodes = args.collect { |a| Server.new(a) }
14
+
15
+ info "Removing #{nodes.size} nodes from load balancer #{lb.id}"
16
+ lb.remove_nodes nodes
17
+ lb.reload
18
+ render_table([lb], global_options)
19
+ end
20
+ end
@@ -0,0 +1,21 @@
1
+ desc 'Show detailed load balancer info'
2
+ arg_name 'lbs-id...'
3
+ command [:show] do |c|
4
+
5
+ c.action do |global_options,options,args|
6
+
7
+ raise "You must specify load balancers to show" if args.empty?
8
+
9
+ lbs = LoadBalancer.find_or_call(args) do |id|
10
+ raise "Couldn't find lb #{id}"
11
+ end
12
+
13
+ table_opts = global_options.merge({
14
+ :vertical => true,
15
+ :fields => [:id, :status, :name, "created_at", "deleted_at", :policy, :cloud_ips, :nodes, :listeners, :healthcheck]
16
+ })
17
+
18
+ render_table(lbs, table_opts)
19
+
20
+ end
21
+ end
@@ -0,0 +1,85 @@
1
+ desc 'Update a load balancer'
2
+ long_desc "All intervals and timeouts are in milliseconds"
3
+ arg_name 'lba-id [node-id...]'
4
+
5
+ command [:update] do |c|
6
+
7
+ c.desc "Friendly name of load balancer"
8
+ c.flag [:n, :name]
9
+
10
+ c.desc "Load balancer policy"
11
+ c.flag [:p, :policy]
12
+
13
+ c.desc "Listeners (in-port:out-port:protocol. Comma separate multiple listeners)"
14
+ c.flag [:l, :listeners]
15
+
16
+ c.desc "Healthcheck port"
17
+ c.flag [:k, "hc-port"]
18
+
19
+ c.desc "Healthcheck type"
20
+ c.flag [:y, "hc-type"]
21
+
22
+ c.desc "Healthcheck timeout"
23
+ c.flag [:t, "hc-timeout"]
24
+
25
+ c.desc "Healthcheck request. When the type is 'http' this is the url to request."
26
+ c.flag [:s, "hc-request"]
27
+
28
+ c.desc "Healthcheck interval"
29
+ c.flag [:e, "hc-interval"]
30
+
31
+ c.desc "Healthcheck threshold up. Number of successful healthchecks for the node to be considered up."
32
+ c.flag [:u, "hc-up"]
33
+
34
+ c.desc "Healthcheck threshold down. Number of failed healthchecks for the node to be considered down."
35
+ c.flag [:d, "hc-down"]
36
+
37
+ c.action do |global_options, options, args|
38
+
39
+ lb_id = args.shift
40
+ raise "You must specify the load balancer to update as the first argument" unless lb_id =~ /^lba-/
41
+
42
+ lbopts = {}
43
+
44
+ unless args.empty?
45
+ lbopts[:nodes] = args.collect { |a| { :node => a } }
46
+ end
47
+
48
+ hc_arg_lookup = { :k => :port, :y => :type, :t => :timeout, :s =>
49
+ :request, :e => :interval, :u => :threshold_up, :d =>
50
+ :threshold_down }
51
+
52
+ healthcheck = {}
53
+
54
+ options.keys.each do |k|
55
+ if options[k] and hc_arg_lookup[k]
56
+ healthcheck[hc_arg_lookup[k]] = options[k]
57
+ end
58
+ end
59
+
60
+ unless healthcheck.keys.empty?
61
+ lbopts[:healthcheck] = healthcheck
62
+ end
63
+
64
+ if options[:l]
65
+ lbopts[:listeners] = options[:l].split(",").collect do |l|
66
+ inport, output, protocol = l.split ":"
67
+ { :in => inport, :out => output, :protocol => protocol }
68
+ end
69
+ end
70
+
71
+ if options[:n]
72
+ lbopts[:name] = options[:n]
73
+ end
74
+
75
+ if options[:p]
76
+ lbopts[:policy] = options[:p]
77
+ end
78
+
79
+ lb = LoadBalancer.find lb_id
80
+
81
+ info "Updating load balancer #{lb}"
82
+ lb = lb.update(lbopts)
83
+ render_table([lb], global_options)
84
+ end
85
+ end
@@ -61,9 +61,16 @@ command [:create] do |c|
61
61
 
62
62
  if user_data_file
63
63
  raise "Cannot specify user data on command line and in file at same time" if user_data
64
- File.open(user_data_file, "r") do |f|
65
- raise "User data file too big (>16k)" if f.stat.size > 16 * 1024
66
- user_data = f.read
64
+ # Wot we use to read the data, be it from stdin or a file on disk
65
+ file_handler = lambda do |fh|
66
+ raise "User data file too big (>16k)" if fh.stat.size > 16 * 1024
67
+ user_data = fh.read
68
+ end
69
+ # Figure out how to invoke file_handler, and then invoke it
70
+ if user_data_file == "-"
71
+ file_handler[$stdin]
72
+ else
73
+ File.open user_data_file, "r", &file_handler
67
74
  end
68
75
  end
69
76
 
@@ -0,0 +1,86 @@
1
+ module Brightbox
2
+ class LoadBalancer < Api
3
+
4
+ def self.create(options)
5
+ new(conn.load_balancers.create(options))
6
+ end
7
+
8
+ def attributes
9
+ fog_model.attributes
10
+ end
11
+
12
+ def to_row
13
+ attributes.merge({ :nodes => node_ids,
14
+ :created_on => created_on,
15
+ :listeners => listeners,
16
+ :cloud_ips => cloud_ips
17
+ })
18
+ end
19
+
20
+ def created_on
21
+ attributes["created_at"].to_s.split('T').first
22
+ end
23
+
24
+ def node_ids
25
+ @node_ids ||= attributes[:nodes].collect { |n| n["id"] } if attributes[:nodes]
26
+ end
27
+
28
+ def cloud_ip_ids
29
+ @cloud_ip_ids ||= attributes["cloud_ips"].collect { |n| n["id"] } if attributes["cloud_ips"]
30
+ end
31
+
32
+ def cloud_ips
33
+ @cloud_ips ||= attributes["cloud_ips"].collect { |n| n["public_ip"] } if attributes["cloud_ips"]
34
+ end
35
+
36
+ def listeners
37
+ if attributes[:listeners]
38
+ attributes[:listeners].collect { |l| [l["in"], l["out"], l["protocol"]].join(":") }
39
+ else
40
+ nil
41
+ end
42
+ end
43
+
44
+ def destroy
45
+ fog_model.destroy
46
+ rescue Excon::Errors::Conflict => e
47
+ raise Conflict, "Cannot delete load balancer #{id}"
48
+ end
49
+
50
+ def add_nodes(nodes)
51
+ node_hashes = nodes.collect { |n| { :node => n.id } }
52
+ LoadBalancer.conn.add_nodes_load_balancer(id, :nodes => node_hashes)
53
+ rescue Excon::Errors::BadRequest => e
54
+ raise Conflict, JSON.parse(e.response.body)['error']['details']
55
+ end
56
+
57
+ def remove_nodes(nodes)
58
+ node_hashes = nodes.collect { |n| { :node => n.id } }
59
+ LoadBalancer.conn.remove_nodes_load_balancer(id, :nodes => node_hashes)
60
+ rescue Excon::Errors::BadRequest => e
61
+ raise Conflict, JSON.parse(e.response.body)['error']['details']
62
+ end
63
+
64
+ def update(options)
65
+ debug options.inspect
66
+ LoadBalancer.conn.update_load_balancer(id, options)
67
+ self.reload
68
+ self
69
+ rescue Excon::Errors::BadRequest => e
70
+ raise Conflict, JSON.parse(e.response.body)['error']['details']
71
+ end
72
+
73
+ def self.get(id)
74
+ conn.load_balancers.get id
75
+ end
76
+
77
+ def self.all
78
+ conn.load_balancers
79
+ end
80
+
81
+ def self.default_field_order
82
+ [:id, :status, :created_on, :cloud_ips, :nodes, :name]
83
+ end
84
+
85
+ end
86
+ end
@@ -1,3 +1,3 @@
1
1
  module Brightbox
2
- VERSION = "0.9.2"
2
+ VERSION = "0.10.1"
3
3
  end
@@ -85,7 +85,7 @@ _brightbox()
85
85
  client_default|client_remove|client_list)
86
86
  ;;
87
87
  *)
88
- COMPREPLY=( $( compgen -W 'client_add client_remove client_default help' -- "$cur" ) )
88
+ COMPREPLY=( $( compgen -W 'client_add client_remove client_default client_list help' -- "$cur" ) )
89
89
  ;;
90
90
  esac
91
91
  ;;
@@ -115,6 +115,24 @@ _brightbox()
115
115
  ;;
116
116
  esac
117
117
  ;;
118
+ brightbox-lbs)
119
+ case $command in
120
+ create|update)
121
+ if [[ "$cur" == -* ]] ; then
122
+ COMPREPLY=( $( compgen -W '--hc-down --hc-interval --port --listeners --name --policy --hc-request --hc-timeout --hc-up --hc-type' -- "$cur" ) )
123
+ else
124
+ test -d ~/.brightbox/cache && COMPREPLY=( $( compgen -W '`ls ~/.brightbox/cache/`' -- "$cur" ) )
125
+ fi
126
+ ;;
127
+ destroy|list|show|remove_nodes|add_nodes)
128
+ test -d ~/.brightbox/cache && COMPREPLY=( $( compgen -W '`ls ~/.brightbox/cache/`' -- "$cur" ) )
129
+ ;;
130
+ *)
131
+ COMPREPLY=( $( compgen -W 'create destroy help list show shutdown snapshot start stop' -- "$cur" ) )
132
+ ;;
133
+ esac
134
+ ;;
135
+
118
136
  esac
119
137
 
120
138
  }
@@ -123,10 +141,11 @@ complete -F _brightbox -o filenames brightbox-images
123
141
  complete -F _brightbox -o filenames brightbox-cloudips
124
142
  complete -F _brightbox -o filenames brightbox-config
125
143
  complete -F _brightbox -o filenames brightbox-users
144
+ complete -F _brightbox -o filenames brightbox-lbs
126
145
 
127
146
  # Local variables:
128
147
  # mode: shell-script
129
- # sh-basic-offset: 4
148
+ # sh-basic-offset: 2
130
149
  # sh-indent-comment: t
131
150
  # indent-tabs-mode: nil
132
151
  # End:
metadata CHANGED
@@ -4,9 +4,9 @@ version: !ruby/object:Gem::Version
4
4
  prerelease: false
5
5
  segments:
6
6
  - 0
7
- - 9
8
- - 2
9
- version: 0.9.2
7
+ - 10
8
+ - 1
9
+ version: 0.10.1
10
10
  platform: ruby
11
11
  authors:
12
12
  - John Leach
@@ -14,7 +14,7 @@ autorequire:
14
14
  bindir: bin
15
15
  cert_chain: []
16
16
 
17
- date: 2010-11-27 00:00:00 +00:00
17
+ date: 2011-01-24 00:00:00 +00:00
18
18
  default_executable:
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency
@@ -57,9 +57,9 @@ dependencies:
57
57
  - !ruby/object:Gem::Version
58
58
  segments:
59
59
  - 1
60
- - 1
61
60
  - 2
62
- version: 1.1.2
61
+ - 5
62
+ version: 1.2.5
63
63
  type: :runtime
64
64
  version_requirements: *id003
65
65
  - !ruby/object:Gem::Dependency
@@ -87,9 +87,9 @@ dependencies:
87
87
  - !ruby/object:Gem::Version
88
88
  segments:
89
89
  - 0
90
- - 3
91
- - 23
92
- version: 0.3.23
90
+ - 4
91
+ - 0
92
+ version: 0.4.0
93
93
  type: :runtime
94
94
  version_requirements: *id005
95
95
  - !ruby/object:Gem::Dependency
@@ -102,9 +102,9 @@ dependencies:
102
102
  - !ruby/object:Gem::Version
103
103
  segments:
104
104
  - 0
105
- - 2
106
- - 4
107
- version: 0.2.4
105
+ - 3
106
+ - 7
107
+ version: 0.3.7
108
108
  type: :runtime
109
109
  version_requirements: *id006
110
110
  - !ruby/object:Gem::Dependency
@@ -130,6 +130,7 @@ executables:
130
130
  - brightbox-cloudips
131
131
  - brightbox-config
132
132
  - brightbox-images
133
+ - brightbox-lbs
133
134
  - brightbox-servers
134
135
  - brightbox-types
135
136
  - brightbox-users
@@ -149,6 +150,7 @@ files:
149
150
  - bin/brightbox-cloudips
150
151
  - bin/brightbox-config
151
152
  - bin/brightbox-images
153
+ - bin/brightbox-lbs
152
154
  - bin/brightbox-servers
153
155
  - bin/brightbox-types
154
156
  - bin/brightbox-users
@@ -174,6 +176,13 @@ files:
174
176
  - lib/bbcloud/commands/images-list.rb
175
177
  - lib/bbcloud/commands/images-register.rb
176
178
  - lib/bbcloud/commands/images-show.rb
179
+ - lib/bbcloud/commands/lbs-add-nodes.rb
180
+ - lib/bbcloud/commands/lbs-create.rb
181
+ - lib/bbcloud/commands/lbs-destroy.rb
182
+ - lib/bbcloud/commands/lbs-list.rb
183
+ - lib/bbcloud/commands/lbs-remove-nodes.rb
184
+ - lib/bbcloud/commands/lbs-show.rb
185
+ - lib/bbcloud/commands/lbs-update.rb
177
186
  - lib/bbcloud/commands/servers-create.rb
178
187
  - lib/bbcloud/commands/servers-destroy.rb
179
188
  - lib/bbcloud/commands/servers-list.rb
@@ -190,6 +199,7 @@ files:
190
199
  - lib/bbcloud/commands/zones-list.rb
191
200
  - lib/bbcloud/config.rb
192
201
  - lib/bbcloud/images.rb
202
+ - lib/bbcloud/load_balancers.rb
193
203
  - lib/bbcloud/servers.rb
194
204
  - lib/bbcloud/tables.rb
195
205
  - lib/bbcloud/types.rb