cf 0.6.1.rc3 → 0.6.1.rc4

Sign up to get free protection for your applications and to get access to all the features.
Files changed (42) hide show
  1. data/lib/cf/cli.rb +6 -3
  2. data/lib/cf/cli/populators/base.rb +14 -0
  3. data/lib/cf/cli/populators/organization.rb +23 -0
  4. data/lib/cf/cli/populators/populator_methods.rb +52 -0
  5. data/lib/cf/cli/populators/space.rb +29 -0
  6. data/lib/cf/cli/populators/target.rb +13 -0
  7. data/lib/cf/cli/service/services.rb +5 -2
  8. data/lib/cf/cli/space/base.rb +6 -0
  9. data/lib/cf/cli/space/spaces.rb +46 -44
  10. data/lib/cf/cli/start/base.rb +7 -56
  11. data/lib/cf/cli/start/login.rb +3 -8
  12. data/lib/cf/cli/start/target.rb +5 -9
  13. data/lib/cf/version.rb +1 -1
  14. data/spec/assets/hello-sinatra/main.rb +5 -3
  15. data/spec/cf/cli/app/scale_spec.rb +5 -1
  16. data/spec/cf/cli/app/start_spec.rb +5 -1
  17. data/spec/cf/cli/domain/map_spec.rb +5 -1
  18. data/spec/cf/cli/domain/unmap_spec.rb +5 -1
  19. data/spec/cf/cli/organization/orgs_spec.rb +1 -1
  20. data/spec/cf/cli/populators/organization_spec.rb +130 -0
  21. data/spec/cf/cli/populators/space_spec.rb +131 -0
  22. data/spec/cf/cli/populators/target_spec.rb +18 -0
  23. data/spec/cf/cli/route/map_spec.rb +5 -1
  24. data/spec/cf/cli/route/unmap_spec.rb +5 -1
  25. data/spec/cf/cli/service/services_spec.rb +72 -0
  26. data/spec/cf/cli/space/create_spec.rb +24 -7
  27. data/spec/cf/cli/space/rename_spec.rb +16 -5
  28. data/spec/cf/cli/space/spaces_spec.rb +12 -2
  29. data/spec/cf/cli/space/switch_space_spec.rb +18 -3
  30. data/spec/cf/cli/start/login_spec.rb +28 -81
  31. data/spec/cf/cli/start/target_spec.rb +33 -32
  32. data/spec/cf/cli/user/register_spec.rb +5 -1
  33. data/spec/cf/cli_spec.rb +21 -1
  34. data/spec/features/account_lifecycle_spec.rb +8 -3
  35. data/spec/features/login_spec.rb +16 -11
  36. data/spec/features/push_flow_spec.rb +26 -11
  37. data/spec/features/switching_targets_spec.rb +42 -2
  38. data/spec/spec_helper.rb +1 -1
  39. data/spec/support/{command_helper.rb → cli_helper.rb} +18 -25
  40. data/spec/support/shared_examples/populate_organization.rb +6 -0
  41. metadata +20 -6
  42. data/lib/cf/cli/start/target_interactions.rb +0 -37
@@ -1,7 +1,7 @@
1
1
  require 'spec_helper'
2
2
  require "cf/cli/space/create"
3
3
 
4
- command CF::Space::Create do
4
+ describe CF::Space::Create do
5
5
  describe 'metadata' do
6
6
  let(:command) { Mothership.commands[:create_space] }
7
7
 
@@ -25,21 +25,29 @@ command CF::Space::Create do
25
25
  end
26
26
 
27
27
  describe "running the command" do
28
- let(:client) do
29
- fake_client(:current_organization => organization)
30
- end
31
-
32
- let(:organization) { fake(:organization) }
33
-
34
28
  let(:new_space) { fake :space, :name => new_name }
35
29
  let(:new_name) { "some-new-name" }
36
30
 
31
+ let(:spaces) { [new_space] }
32
+ let(:organization) { fake(:organization, :spaces => spaces) }
33
+
34
+ let(:client) { fake_client(:current_organization => organization, :spaces => spaces) }
35
+
36
+
37
+
37
38
  before do
38
39
  stub(client).space { new_space }
39
40
  stub(new_space).create!
40
41
  stub(new_space).add_manager
41
42
  stub(new_space).add_developer
42
43
  stub(new_space).add_auditor
44
+ any_instance_of described_class do |cli|
45
+ stub(cli).client { client }
46
+
47
+ stub(cli).check_logged_in
48
+ stub(cli).check_target
49
+ stub(cli).check_organization
50
+ end
43
51
  end
44
52
 
45
53
  context "when --target is given" do
@@ -59,6 +67,15 @@ command CF::Space::Create do
59
67
  subject
60
68
  expect(output).to say("Space created! Use switch-space #{new_space.name} to target it.")
61
69
  end
70
+
71
+ it_should_behave_like "a_command_that_populates_organization" do
72
+ before do
73
+ any_instance_of described_class do |cli|
74
+ stub.proxy(cli).check_organization
75
+ end
76
+ end
77
+ end
78
+
62
79
  end
63
80
 
64
81
  context "when we don't specify an organization" do
@@ -10,7 +10,10 @@ describe CF::Space::Rename do
10
10
  before do
11
11
  any_instance_of described_class do |cli|
12
12
  stub(cli).client { client }
13
- stub(cli).precondition { nil }
13
+
14
+ stub(cli).check_logged_in
15
+ stub(cli).check_target
16
+ stub(cli).check_organization
14
17
  end
15
18
  end
16
19
 
@@ -29,8 +32,8 @@ describe CF::Space::Rename do
29
32
  subject { command.arguments }
30
33
  it 'has the correct argument order' do
31
34
  should eq([
32
- { :type => :optional, :value => nil, :name => :space },
33
- { :type => :optional, :value => nil, :name => :name }
35
+ {:type => :optional, :value => nil, :name => :space},
36
+ {:type => :optional, :value => nil, :name => :name}
34
37
  ])
35
38
  end
36
39
  end
@@ -58,10 +61,9 @@ describe CF::Space::Rename do
58
61
 
59
62
  context 'when there are spaces' do
60
63
  let(:renamed_space) { spaces.first }
64
+ subject { cf %W[rename-space --no-force --no-quiet] }
61
65
 
62
66
  context 'when the defaults are used' do
63
- subject { cf %W[rename-space --no-force --no-quiet] }
64
-
65
67
  it 'asks for the space and new name and renames' do
66
68
  mock_ask("Rename which space?", anything) { renamed_space }
67
69
  mock_ask("New name") { new_name }
@@ -74,6 +76,15 @@ describe CF::Space::Rename do
74
76
  context 'when no name is provided, but a space is' do
75
77
  subject { cf %W[rename-space --space #{renamed_space.name} --no-force] }
76
78
 
79
+ it_should_behave_like "a_command_that_populates_organization" do
80
+ subject { cf %W[rename-space --no-force --no-quiet #{renamed_space}] }
81
+ before do
82
+ any_instance_of described_class do |cli|
83
+ stub.proxy(cli).check_organization
84
+ end
85
+ end
86
+ end
87
+
77
88
  it 'asks for the new name and renames' do
78
89
  dont_allow_ask("Rename which space?", anything)
79
90
  mock_ask("New name") { new_name }
@@ -13,7 +13,9 @@ describe CF::Space::Spaces do
13
13
  before do
14
14
  any_instance_of described_class do |cli|
15
15
  stub(cli).client { client }
16
- stub(cli).precondition { nil }
16
+ stub(cli).check_logged_in
17
+ stub(cli).check_target
18
+ stub(cli).check_organization
17
19
  end
18
20
  end
19
21
 
@@ -38,7 +40,7 @@ describe CF::Space::Spaces do
38
40
 
39
41
  subject { cf %W[spaces --#{bool_flag(:full)} --no-quiet] }
40
42
 
41
- it 'should have the correct first two lines' do
43
+ it 'outputs that it is getting spaces' do
42
44
  subject
43
45
 
44
46
  stdout.rewind
@@ -72,6 +74,14 @@ describe CF::Space::Spaces do
72
74
  end
73
75
 
74
76
  context 'when there are spaces' do
77
+ it_should_behave_like "a_command_that_populates_organization" do
78
+ before do
79
+ any_instance_of described_class do |cli|
80
+ stub.proxy(cli).check_organization
81
+ end
82
+ end
83
+ end
84
+
75
85
  context 'and the full flag is given' do
76
86
  let(:full) { true }
77
87
 
@@ -10,8 +10,12 @@ describe CF::Space::Switch do
10
10
  before do
11
11
  any_instance_of described_class do |cli|
12
12
  stub(cli).client { client }
13
- stub(cli).precondition { nil }
13
+
14
+ stub(cli).check_logged_in
15
+ stub(cli).check_target
16
+ stub(cli).check_organization
14
17
  end
18
+
15
19
  end
16
20
 
17
21
  describe 'metadata' do
@@ -28,21 +32,32 @@ describe CF::Space::Switch do
28
32
  describe 'arguments' do
29
33
  subject { command.arguments }
30
34
  it 'has the correct argument order' do
31
- should eq([{ :type => :normal, :value => nil, :name => :name }])
35
+ should eq([{:type => :normal, :value => nil, :name => :name}])
32
36
  end
33
37
  end
34
38
  end
35
39
 
36
40
  subject { cf %W[--no-quiet switch-space #{space_to_switch_to.name} --no-color] }
37
41
 
42
+
38
43
  context "when the space exists" do
39
- it "switches to that space" do
44
+ before do
40
45
  any_instance_of(Mothership) do |m|
41
46
  mock(m).invoke(:target, {:space => space_to_switch_to})
42
47
  end
48
+ end
43
49
 
50
+ it "switches to that space" do
44
51
  subject
45
52
  end
53
+
54
+ it_should_behave_like "a_command_that_populates_organization" do
55
+ before do
56
+ any_instance_of described_class do |cli|
57
+ stub.proxy(cli).check_organization
58
+ end
59
+ end
60
+ end
46
61
  end
47
62
 
48
63
  context "when the space does not exist" do
@@ -1,9 +1,13 @@
1
1
  require 'spec_helper'
2
2
 
3
- command CF::Start::Login do
4
- let(:client) { fake_client :organizations => [] }
3
+ describe CF::Start::Login do
4
+ let(:client) { fake_client }
5
5
 
6
6
  describe 'metadata' do
7
+ before do
8
+ stub_client_and_precondition
9
+ end
10
+
7
11
  let(:command) { Mothership.commands[:login] }
8
12
 
9
13
  describe 'command' do
@@ -32,12 +36,15 @@ command CF::Start::Login do
32
36
  end
33
37
 
34
38
  describe "running the command" do
39
+ before do
40
+ stub_client
41
+ end
42
+
35
43
  stub_home_dir_with { "#{SPEC_ROOT}/fixtures/fake_home_dirs/new" }
36
44
 
37
45
  let(:auth_token) { CFoundry::AuthToken.new("bearer some-new-access-token", "some-new-refresh-token") }
38
46
  let(:tokens_yaml) { YAML.load_file(File.expand_path(tokens_file_path)) }
39
47
  let(:tokens_file_path) { '~/.cf/tokens.yml' }
40
- let(:organizations) { [] }
41
48
 
42
49
  before do
43
50
  stub(client).login("my-username", "my-password") { auth_token }
@@ -47,105 +54,45 @@ command CF::Start::Login do
47
54
  :password => ["password", "8-digit PIN"]
48
55
  }
49
56
  end
50
- end
51
57
 
52
- subject { cf ["login"] }
53
-
54
- it "logs in with the provided credentials and saves the token data to the YAML file" do
55
58
  stub_ask("Username", {}) { "my-username" }
56
59
  stub_ask("8-digit PIN", {:echo => "*", :forget => true}) { "my-password" }
57
-
58
- subject
59
-
60
- expect(tokens_yaml["https://api.some-domain.com"][:token]).to eq("bearer some-new-access-token")
61
- expect(tokens_yaml["https://api.some-domain.com"][:refresh_token]).to eq("some-new-refresh-token")
60
+ any_instance_of(CF::Populators::Target, :populate_and_save! => true)
62
61
  end
63
62
 
64
- context "when the user logs in with invalid credentials" do
65
- before do
66
- stub_ask("Username", {}) { "my-username" }
67
- stub_ask("8-digit PIN", {:echo => "*", :forget => true}) { "my-password" }
63
+ subject { cf ["login"] }
68
64
 
69
- stub(client).login("my-username", "my-password") { raise CFoundry::Denied }
65
+ context "when there is a target" do
66
+ before do
67
+ stub_precondition
70
68
  end
71
69
 
72
- it "informs the user gracefully" do
70
+ it "logs in with the provided credentials and saves the token data to the YAML file" do
73
71
  subject
74
- expect(output).to say("Authenticating... FAILED")
75
- end
76
- end
77
72
 
78
- context "with space and org in the token file" do
79
- before do
80
- write_token_file(:space => "space-id-1", :organization => "organization-id-1")
81
- stub_ask("Username", {}) { "my-username" }
82
- stub_ask("8-digit PIN", {:echo => "*", :forget => true}) { "my-password" }
73
+ expect(tokens_yaml["https://api.some-domain.com"][:token]).to eq("bearer some-new-access-token")
74
+ expect(tokens_yaml["https://api.some-domain.com"][:refresh_token]).to eq("some-new-refresh-token")
83
75
  end
84
76
 
85
- context "when the user has no organizations" do
86
- it "clears the org and space param from the token file" do
87
- subject
88
-
89
- expect(tokens_yaml["https://api.some-domain.com"][:space]).to be_nil
90
- expect(tokens_yaml["https://api.some-domain.com"][:organization]).to be_nil
91
- end
77
+ it "calls use a PopulateTarget to ensure that an organization and space is set" do
78
+ mock(CF::Populators::Target).new(is_a(Mothership::Inputs)) { mock!.populate_and_save! }
79
+ subject
92
80
  end
93
81
 
94
- context "when the user has an organization, but no spaces" do
95
- let(:client) {
96
- fake_client :organizations => organizations,
97
- :token => CFoundry::AuthToken.new("bearer some-access-token")
98
- }
99
- let(:organization) { fake :organization, :users => [user] }
100
- let(:user) { fake :user }
101
-
102
- shared_examples_for :method_clearing_the_token_file do
103
- it "sets the new organization in the token file" do
104
- subject
105
- expect(tokens_yaml["https://api.some-domain.com"][:organization]).to eq(organizations.first.guid)
106
- end
107
-
108
- it "clears the space param from the token file" do
109
- subject
110
- expect(tokens_yaml["https://api.some-domain.com"][:space]).to be_nil
111
- end
82
+ context "when the user logs in with invalid credentials" do
83
+ before do
84
+ stub(client).login("my-username", "my-password") { raise CFoundry::Denied }
112
85
  end
113
86
 
114
- context "with one organization" do
115
- let(:organizations) {
116
- [organization]
117
- }
118
-
119
- it "does not prompt for an organization" do
120
- dont_allow_ask("Organization", anything)
121
- subject
122
- end
123
-
124
- it_behaves_like :method_clearing_the_token_file
125
- end
126
-
127
- context "with multiple organizations" do
128
- let(:organizations) {
129
- [organization, OpenStruct.new(:name => 'My Org 2', :guid => 'organization-id-2')]
130
- }
131
-
132
- before do
133
- stub_ask("Organization", anything) { organizations.first }
134
- end
135
-
136
- it "prompts for organization" do
137
- mock_ask("Organization", anything) { organizations.first }
138
- subject
139
- end
140
-
141
- it_behaves_like :method_clearing_the_token_file
87
+ it "informs the user gracefully" do
88
+ subject
89
+ expect(output).to say("Authenticating... FAILED")
142
90
  end
143
91
  end
144
92
  end
145
93
 
146
- context 'when there is no target' do
94
+ context "when there is no target" do
147
95
  let(:client) { nil }
148
- let(:stub_precondition?) { false }
149
96
 
150
97
  it "tells the user to select a target" do
151
98
  subject
@@ -1,22 +1,26 @@
1
- require 'spec_helper'
1
+ require "spec_helper"
2
2
  require "webmock/rspec"
3
3
 
4
- command CF::Start::Target do
4
+ describe CF::Start::Target do
5
+ before do
6
+ stub_client_and_precondition
7
+ end
8
+
5
9
  let(:client) { fake_client :apps => [app] }
6
10
  let(:app) { fake :app }
7
11
 
8
- describe 'metadata' do
12
+ describe "metadata" do
9
13
  let(:command) { Mothership.commands[:target] }
10
14
 
11
- describe 'command' do
15
+ describe "command" do
12
16
  subject { command }
13
17
  its(:description) { should eq "Set or display the target cloud, organization, and space" }
14
18
  specify { expect(Mothership::Help.group(:start)).to include(subject) }
15
19
  end
16
20
 
17
- include_examples 'inputs must have descriptions'
21
+ include_examples "inputs must have descriptions"
18
22
 
19
- describe 'flags' do
23
+ describe "flags" do
20
24
  subject { command.flags }
21
25
 
22
26
  its(["-o"]) { should eq :organization }
@@ -24,36 +28,24 @@ command CF::Start::Target do
24
28
  its(["-s"]) { should eq :space }
25
29
  end
26
30
 
27
- describe 'arguments' do
31
+ describe "arguments" do
28
32
  subject(:arguments) { command.arguments }
29
- it 'have the correct commands' do
33
+ it "have the correct commands" do
30
34
  expect(arguments).to eq [{:type => :optional, :value => nil, :name => :url}]
31
35
  end
32
36
  end
33
37
  end
34
38
 
35
- describe 'running the command' do
39
+ describe "running the command" do
36
40
  stub_home_dir_with { "#{SPEC_ROOT}/fixtures/fake_home_dirs/new" }
37
41
 
38
42
  context "when the user is authenticated and has an organization" do
39
- let(:tokens_file_path) { '~/.cf/tokens.yml' }
40
- let(:organizations) {
41
- [ fake(:organization, :name => 'My Org', :guid => 'organization-id-1', :users => [user], :spaces => spaces),
42
- fake(:organization, :name => 'My Org 2', :guid => 'organization-id-2') ]
43
- }
44
- let(:spaces) {
45
- [ fake(:space, :name => 'Development', :guid => 'space-id-1'),
46
- fake(:space, :name => 'Staging', :guid => 'space-id-2') ]
47
- }
48
-
49
43
  let(:user) { stub! }
50
- let(:organization) { organizations.first }
51
- let(:client) do
52
- fake_client :organizations => organizations, :token => CFoundry::AuthToken.new("bearer some-access-token")
53
- end
44
+ let(:organization) { fake(:organization, :name => "My Org", :guid => "organization-id-1", :users => [user], :spaces => [space]) }
45
+ let(:space) { fake(:space, :name => "Staging", :guid => "space-id-2", :developers => [user]) }
46
+ let(:client) { fake_client :organizations => [organization], :token => CFoundry::AuthToken.new("bearer some-access-token") }
54
47
 
55
48
  before do
56
- write_token_file({:space => "space-id-1", :organization => "organization-id-1"})
57
49
  stub(client).current_user { user }
58
50
  stub(client).organization { organization }
59
51
  stub(client).current_organization { organization }
@@ -98,24 +90,33 @@ command CF::Start::Target do
98
90
  end
99
91
 
100
92
  describe "switching the space" do
101
- let(:space) { spaces.last }
102
- let(:tokens_yaml) { YAML.load_file(File.expand_path(tokens_file_path)) }
103
- let(:tokens_file_path) { '~/.cf/tokens.yml' }
104
-
105
93
  def run_command
106
94
  cf %W[target -s #{space.name}]
107
95
  end
108
96
 
109
- it "should not reprompt for organization" do
110
- dont_allow_ask("Organization", anything)
97
+ it "calls use a PopulateTarget to ensure that an organization and space is set" do
98
+ mock(CF::Populators::Target).new(is_a(Mothership::Inputs)) { mock!.populate_and_save! }
111
99
  run_command
112
100
  end
113
101
 
114
- it "sets the space param in the token file" do
102
+ it "prints out the space from the updated client" do
103
+ any_instance_of(CF::Populators::Target, :populate_and_save! => true)
104
+ stub(client).current_space { space }
105
+
115
106
  run_command
116
- expect(tokens_yaml["https://api.some-domain.com"][:space]).to be == 'space-id-2'
107
+ expect(output).to say("space: #{space.name}")
117
108
  end
118
109
  end
119
110
  end
111
+
112
+ context "when client is nil" do
113
+ let(:client) { nil }
114
+ subject { cf ["target"] }
115
+
116
+ it 'prints an error' do
117
+ subject
118
+ expect(error_output).to say("No target has been specified.")
119
+ end
120
+ end
120
121
  end
121
122
  end