oauth2_provider_engine 0.0.1

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.
Files changed (132) hide show
  1. data/MIT-LICENSE +20 -0
  2. data/README.rdoc +3 -0
  3. data/Rakefile +40 -0
  4. data/app/assets/javascripts/oauth2_provider/application.js +52 -0
  5. data/app/assets/javascripts/oauth2_provider/highcharts.js +162 -0
  6. data/app/assets/javascripts/oauth2_provider/jquery.tagsinput.js +218 -0
  7. data/app/assets/stylesheets/oauth2_provider/gh-buttons.css +388 -0
  8. data/app/assets/stylesheets/oauth2_provider/gh-icons.png +0 -0
  9. data/app/assets/stylesheets/oauth2_provider/jquery.tagsinput.css +6 -0
  10. data/app/assets/stylesheets/oauth2_provider/reset.css +2 -0
  11. data/app/assets/stylesheets/oauth2_provider/template.css +52 -0
  12. data/app/controllers/oauth2_provider/accesses_controller.rb +39 -0
  13. data/app/controllers/oauth2_provider/application_controller.rb +17 -0
  14. data/app/controllers/oauth2_provider/authorize_controller.rb +141 -0
  15. data/app/controllers/oauth2_provider/clients_controller.rb +85 -0
  16. data/app/controllers/oauth2_provider/scopes_controller.rb +63 -0
  17. data/app/controllers/oauth2_provider/token_controller.rb +187 -0
  18. data/app/helpers/clients_helper.rb +5 -0
  19. data/app/helpers/oauth2_provider/application_helper.rb +4 -0
  20. data/app/models/oauth2_provider/client.rb +129 -0
  21. data/app/models/oauth2_provider/document.rb +15 -0
  22. data/app/models/oauth2_provider/oauth_access.rb +80 -0
  23. data/app/models/oauth2_provider/oauth_authorization.rb +70 -0
  24. data/app/models/oauth2_provider/oauth_daily_request.rb +54 -0
  25. data/app/models/oauth2_provider/oauth_refresh_token.rb +20 -0
  26. data/app/models/oauth2_provider/oauth_token.rb +78 -0
  27. data/app/models/oauth2_provider/scope.rb +39 -0
  28. data/app/views/layouts/oauth2_provider/application.html.erb +62 -0
  29. data/app/views/oauth2_provider/accesses/index.html.erb +25 -0
  30. data/app/views/oauth2_provider/accesses/show.html.erb +35 -0
  31. data/app/views/oauth2_provider/clients/_form.html.erb +50 -0
  32. data/app/views/oauth2_provider/clients/edit.html.erb +9 -0
  33. data/app/views/oauth2_provider/clients/index.html.erb +43 -0
  34. data/app/views/oauth2_provider/clients/new.html.erb +8 -0
  35. data/app/views/oauth2_provider/clients/show.html.erb +49 -0
  36. data/app/views/oauth2_provider/scopes/_form.html.erb +35 -0
  37. data/app/views/oauth2_provider/scopes/edit.html.erb +8 -0
  38. data/app/views/oauth2_provider/scopes/index.html.erb +27 -0
  39. data/app/views/oauth2_provider/scopes/new.html.erb +7 -0
  40. data/app/views/oauth2_provider/scopes/show.html.erb +19 -0
  41. data/app/views/shared/authorize.html.erb +34 -0
  42. data/app/views/shared/token.json.erb +8 -0
  43. data/config/locales/en.yml +31 -0
  44. data/config/oauth.yml +4 -0
  45. data/config/routes.rb +25 -0
  46. data/lib/oauth2_provider.rb +38 -0
  47. data/lib/oauth2_provider/controller_mixin.rb +53 -0
  48. data/lib/oauth2_provider/engine.rb +4 -0
  49. data/lib/oauth2_provider_engine.rb +1 -0
  50. data/lib/oauth2_provider_engine/version.rb +3 -0
  51. data/test/dummy/CHANGELOG.rdoc +67 -0
  52. data/test/dummy/Gemfile +53 -0
  53. data/test/dummy/Gemfile.lock +254 -0
  54. data/test/dummy/README.rdoc +522 -0
  55. data/test/dummy/Rakefile +7 -0
  56. data/test/dummy/VERSION +1 -0
  57. data/test/dummy/app/assets/stylesheets/reset.css +2 -0
  58. data/test/dummy/app/assets/stylesheets/template.css +52 -0
  59. data/test/dummy/app/controllers/application_controller.rb +52 -0
  60. data/test/dummy/app/controllers/pastas_controller.rb +23 -0
  61. data/test/dummy/app/controllers/pizzas_controller.rb +23 -0
  62. data/test/dummy/app/controllers/sessions_controller.rb +26 -0
  63. data/test/dummy/app/controllers/users_controller.rb +59 -0
  64. data/test/dummy/app/models/user.rb +50 -0
  65. data/test/dummy/app/views/layouts/application.html.erb +65 -0
  66. data/test/dummy/app/views/sessions/new.html.erb +25 -0
  67. data/test/dummy/app/views/shared/403.json.erb +4 -0
  68. data/test/dummy/app/views/shared/404.json.erb +6 -0
  69. data/test/dummy/app/views/shared/422.json.erb +5 -0
  70. data/test/dummy/app/views/shared/500.json.erb +4 -0
  71. data/test/dummy/app/views/shared/html/404.html.erb +0 -0
  72. data/test/dummy/app/views/shared/html/422.html.erb +0 -0
  73. data/test/dummy/app/views/users/_form.html.erb +27 -0
  74. data/test/dummy/app/views/users/edit.html.erb +8 -0
  75. data/test/dummy/app/views/users/index.html.erb +20 -0
  76. data/test/dummy/app/views/users/new.html.erb +46 -0
  77. data/test/dummy/app/views/users/show.html.erb +15 -0
  78. data/test/dummy/app/views/users/show.json.erb +6 -0
  79. data/test/dummy/config.ru +4 -0
  80. data/test/dummy/config/application.rb +57 -0
  81. data/test/dummy/config/boot.rb +13 -0
  82. data/test/dummy/config/cucumber.yml +8 -0
  83. data/test/dummy/config/environment.rb +5 -0
  84. data/test/dummy/config/environments/development.rb +32 -0
  85. data/test/dummy/config/environments/production.rb +58 -0
  86. data/test/dummy/config/environments/test.rb +35 -0
  87. data/test/dummy/config/initializers/backtrace_silencers.rb +7 -0
  88. data/test/dummy/config/initializers/inflections.rb +10 -0
  89. data/test/dummy/config/initializers/mime_types.rb +5 -0
  90. data/test/dummy/config/initializers/secret_token.rb +7 -0
  91. data/test/dummy/config/initializers/session_store.rb +8 -0
  92. data/test/dummy/config/initializers/test.rb +3 -0
  93. data/test/dummy/config/locales/en.yml +1 -0
  94. data/test/dummy/config/mongoid.yml +20 -0
  95. data/test/dummy/config/routes.rb +22 -0
  96. data/test/dummy/db/seeds.rb +7 -0
  97. data/test/dummy/doc/README_FOR_APP +2 -0
  98. data/test/dummy/lib/tasks/cucumber.rake +53 -0
  99. data/test/dummy/lib/tasks/watchr.rake +5 -0
  100. data/test/dummy/public/404.html +26 -0
  101. data/test/dummy/public/422.html +26 -0
  102. data/test/dummy/public/500.html +4 -0
  103. data/test/dummy/public/favicon.ico +0 -0
  104. data/test/dummy/public/robots.txt +5 -0
  105. data/test/dummy/script/cucumber +10 -0
  106. data/test/dummy/script/rails +6 -0
  107. data/test/dummy/spec/acceptance/acceptance_helper.rb +5 -0
  108. data/test/dummy/spec/acceptance/accesses_controller_spec.rb +77 -0
  109. data/test/dummy/spec/acceptance/clients_controller_spec.rb +218 -0
  110. data/test/dummy/spec/acceptance/oauth_authorize_controller_spec.rb +241 -0
  111. data/test/dummy/spec/acceptance/oauth_token_controller_spec.rb +196 -0
  112. data/test/dummy/spec/acceptance/resource_controller_spec.rb +143 -0
  113. data/test/dummy/spec/acceptance/scopes_controller_spec.rb +227 -0
  114. data/test/dummy/spec/acceptance/support/helpers.rb +81 -0
  115. data/test/dummy/spec/acceptance/support/paths.rb +9 -0
  116. data/test/dummy/spec/acceptance/support/view_helpers.rb +52 -0
  117. data/test/dummy/spec/acceptance/users_controller_spec.rb +198 -0
  118. data/test/dummy/spec/extras/scope_spec.rb +105 -0
  119. data/test/dummy/spec/factories/oauth.rb +106 -0
  120. data/test/dummy/spec/models/oauth/client_spec.rb +123 -0
  121. data/test/dummy/spec/models/oauth/oauth_access_spec.rb +48 -0
  122. data/test/dummy/spec/models/oauth/oauth_authorization_spec.rb +50 -0
  123. data/test/dummy/spec/models/oauth/oauth_daily_request_spec.rb +14 -0
  124. data/test/dummy/spec/models/oauth/oauth_refresh_token_spec.rb +11 -0
  125. data/test/dummy/spec/models/oauth/oauth_token_spec.rb +55 -0
  126. data/test/dummy/spec/models/scope_spec.rb +17 -0
  127. data/test/dummy/spec/spec_helper.rb +39 -0
  128. data/test/dummy/spec/support/settings_helper.rb +28 -0
  129. data/test/dummy/test/initializers/capybara_headers_hack.rb +23 -0
  130. data/test/oauth2_provider_test.rb +7 -0
  131. data/test/test_helper.rb +15 -0
  132. metadata +387 -0
@@ -0,0 +1,196 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/acceptance_helper')
2
+
3
+ feature "OauthTokenController" do
4
+ before { Oauth2Provider::Client.destroy_all }
5
+ before { Oauth2Provider::OauthAccess.destroy_all }
6
+ before { Oauth2Provider::OauthRefreshToken.destroy_all }
7
+
8
+ let(:user) { FactoryGirl.create(:user) }
9
+ let(:client) { FactoryGirl.create(:client) }
10
+ let(:client_read) { FactoryGirl.create(:client_read) }
11
+ let(:authorization) { FactoryGirl.create(:oauth_authorization) }
12
+ let(:access) { FactoryGirl.create(:oauth_access) }
13
+ let(:write_scope) { "pizzas" }
14
+ let(:read_scope) { "pizzas/read" }
15
+
16
+ before { @scope = FactoryGirl.create(:scope_pizzas_read) }
17
+ before { @scope = FactoryGirl.create(:scope_pizzas_all) }
18
+ before { Oauth2Provider::TokenController.any_instance.stub(:user_url).and_return( USER_URI ) }
19
+
20
+ context "Authorization token flow" do
21
+
22
+ let(:attributes) { {
23
+ grant_type: "authorization_code",
24
+ client_id: client.uri,
25
+ client_secret: client.secret,
26
+ code: authorization.code,
27
+ redirect_uri: client.redirect_uri
28
+ } }
29
+
30
+ scenario "create a token" do
31
+ create_token_uri(attributes)
32
+ response_should_have_access_token
33
+ response_should_have_refresh_token
34
+ end
35
+
36
+ context "when client is blocked" do
37
+ it "should not load authorization page" do
38
+ client.block!
39
+ create_token_uri(attributes)
40
+ page.should have_content "Client blocked"
41
+ end
42
+ end
43
+
44
+ context "when access is blocked (resource owner block a client)" do
45
+ it "should not load authorization page" do
46
+ access.block!
47
+ create_token_uri(attributes)
48
+ page.should have_content "Client blocked from the user"
49
+ end
50
+ end
51
+
52
+ context "when not valid" do
53
+ scenario "fails with not valid code" do
54
+ attributes.merge!(code: "not_existing")
55
+ create_token_uri(attributes)
56
+ page.should have_content "Authorization not found"
57
+ end
58
+
59
+ scenario "fails with no valid client uri" do
60
+ attributes.merge!(client_id: "not_existing")
61
+ create_token_uri(attributes)
62
+ page.should have_content "Client not found"
63
+ end
64
+
65
+ scenario "fails when authorization is expired" do
66
+ authorization.expire_at # hack (otherwise do not set the time)
67
+ Delorean.time_travel_to("in #{Oauth2Provider.settings["authorization_expires_in"]} seconds")
68
+ create_token_uri(attributes)
69
+ page.should have_content "Authorization expired"
70
+ page.should have_content "less than 5 seconds"
71
+ end
72
+
73
+ end
74
+ end
75
+
76
+
77
+ context "Password credentials flow" do
78
+ let(:attributes) { {
79
+ grant_type: "password",
80
+ client_id: client.uri,
81
+ client_secret: client.secret,
82
+ username: user.email,
83
+ password: user.password,
84
+ scope: write_scope
85
+ } }
86
+
87
+ scenario "create a token" do
88
+ create_token_uri(attributes)
89
+ response_should_have_access_token
90
+ response_should_have_refresh_token
91
+ end
92
+
93
+ context "when client is blocked" do
94
+ it "should not load authorization page" do
95
+ client.block!
96
+ create_token_uri(attributes)
97
+ page.should have_content "Client blocked"
98
+ end
99
+ end
100
+
101
+ context "when access is blocked (resource owner block a client)" do
102
+ it "should not load authorization page" do
103
+ access.block!
104
+ create_token_uri(attributes)
105
+ page.should have_content "Client blocked from the user"
106
+ end
107
+ end
108
+
109
+ context "when not valid" do
110
+ scenario "fails with not valid user password" do
111
+ attributes.merge!(password: "not_existing")
112
+ create_token_uri(attributes)
113
+ page.should have_content "User not found"
114
+ end
115
+
116
+ scenario "fails with no valid client uri" do
117
+ attributes.merge!(client_id: "not_existing")
118
+ create_token_uri(attributes)
119
+ page.should have_content "Client not found"
120
+ end
121
+
122
+ scenario "fails with no valid scope authorization" do
123
+ attributes.merge!({client_id: client_read.uri, client_secret: client_read.secret })
124
+ create_token_uri(attributes)
125
+ page.should have_content "Client not authorized"
126
+ end
127
+ end
128
+ end
129
+
130
+
131
+ context "Refresh Token" do
132
+ let(:token) { FactoryGirl.create(:oauth_token) }
133
+ let(:refresh_token) { Oauth2Provider::OauthRefreshToken.create(access_token: token.token) }
134
+
135
+ let(:attributes) { {
136
+ grant_type: "refresh_token",
137
+ refresh_token: refresh_token.refresh_token,
138
+ client_id: client.uri,
139
+ client_secret: client.secret
140
+ } }
141
+
142
+ scenario "create an access token" do
143
+ create_token_uri(attributes)
144
+ response_should_have_access_token
145
+ response_should_have_refresh_token
146
+ end
147
+
148
+ context "when client is blocked" do
149
+ scenario "should not load authorization page" do
150
+ client.block!
151
+ create_token_uri(attributes)
152
+ page.should have_content "Client blocked"
153
+ end
154
+ end
155
+
156
+ context "when access is blocked (resource owner block a client)" do
157
+ scenario "should not load authorization page" do
158
+ access.block!
159
+ create_token_uri(attributes)
160
+ page.should have_content "Client blocked from the user"
161
+ end
162
+ end
163
+
164
+ context "when token is blocked (resource owner log out)" do
165
+ scenario "should not load authorization page" do
166
+ token.block!
167
+ create_token_uri(attributes)
168
+ page.should have_content "Access token blocked from the user"
169
+ end
170
+ end
171
+
172
+ context "when not valid" do
173
+ scenario "fails with no valid client uri" do
174
+ attributes.merge!(client_id: "not_existing")
175
+ create_token_uri(attributes)
176
+ page.should have_content "Client not found"
177
+ end
178
+
179
+ scenario "fails with no valid refresh token" do
180
+ attributes.merge!(refresh_token: "not_existing")
181
+ create_token_uri(attributes)
182
+ page.should have_content "Refresh token not found"
183
+ end
184
+ end
185
+ end
186
+
187
+ context "Authorization token flow" do
188
+ before { @token = FactoryGirl.create(:oauth_token) }
189
+
190
+ scenario "block a token" do
191
+ page.driver.delete("/oauth/token/" + @token.token)
192
+ #@token.reload.should be_blocked
193
+ #page.status_code.should == 200
194
+ end
195
+ end
196
+ end
@@ -0,0 +1,143 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/acceptance_helper')
2
+
3
+ feature "ResourceController" do
4
+
5
+ context "with not existing access token" do
6
+ before { @token = FactoryGirl.create(:oauth_access) }
7
+ before { @token = FactoryGirl.create(:oauth_token) }
8
+ before { @token_value = @token.token }
9
+ before do
10
+ uri = Addressable::URI.new
11
+ uri.query_values = {token: @token_value}
12
+ @token_query = uri.query
13
+ end
14
+ before { @token.destroy }
15
+
16
+ scenario ".index" do
17
+ visit "/pizzas?token=" + @token_value
18
+ should_not_be_authorized
19
+ end
20
+
21
+ scenario ".show" do
22
+ visit "/pizzas/0?token=" + @token_value
23
+ should_not_be_authorized
24
+ end
25
+
26
+ scenario ".create" do
27
+ page.driver.post("/pizzas", @token_query)
28
+ should_not_be_authorized
29
+ end
30
+
31
+ scenario ".update" do
32
+ page.driver.put("/pizzas/0", @token_query)
33
+ should_not_be_authorized
34
+ end
35
+
36
+ scenario ".destroy" do
37
+ page.driver.delete("/pizzas/0", @token_query)
38
+ should_not_be_authorized
39
+ end
40
+ end
41
+
42
+ context "with single action accesses" do
43
+ before { @token_value = FactoryGirl.create(:oauth_token, scope: ["pizzas/index"]).token }
44
+ before do
45
+ uri = Addressable::URI.new
46
+ uri.query_values = {token: @token_value}
47
+ @token_query = uri.query
48
+ end
49
+
50
+ scenario ".index" do
51
+ visit "/pizzas?token=" + @token_value
52
+ page.should have_content "index"
53
+ end
54
+
55
+ scenario ".show" do
56
+ visit "/pizzas/0?token=" + @token_value
57
+ should_not_be_authorized
58
+ end
59
+ end
60
+
61
+
62
+ context "with read accesses on a resource" do
63
+ before { @token_value = FactoryGirl.create(:oauth_token_read).token }
64
+ before do
65
+ uri = Addressable::URI.new
66
+ uri.query_values = {token: @token_value}
67
+ @token_query = uri.query
68
+ end
69
+
70
+ scenario ".index" do
71
+ visit "/pizzas?token=" + @token_value
72
+ page.should have_content "index"
73
+ end
74
+
75
+ scenario ".show" do
76
+ visit "/pizzas/0?token=" + @token_value
77
+ page.should have_content "show"
78
+ end
79
+
80
+ scenario ".create" do
81
+ page.driver.post("/pizzas", @token_query)
82
+ should_not_be_authorized
83
+ end
84
+
85
+ scenario ".update" do
86
+ page.driver.put("/pizzas/0", @token_query)
87
+ should_not_be_authorized
88
+ end
89
+
90
+ scenario ".destroy" do
91
+ page.driver.delete("/pizzas/0", @token_query)
92
+ should_not_be_authorized
93
+ end
94
+ end
95
+
96
+
97
+ context "with all accesses" do
98
+ before { @token_value = FactoryGirl.create(:oauth_token).token }
99
+ before do
100
+ uri = Addressable::URI.new
101
+ uri.query_values = {token: @token_value}
102
+ @token_query = uri.query
103
+ end
104
+
105
+ scenario ".index" do
106
+ visit "/pizzas?token=" + @token_value
107
+ page.should have_content "index"
108
+ end
109
+
110
+ scenario ".show" do
111
+ visit "/pizzas/0?token=" + @token_value
112
+ page.should have_content "show"
113
+ end
114
+
115
+ scenario ".create" do
116
+ page.driver.post("/pizzas", @token_query)
117
+ page.should have_content "create"
118
+ end
119
+
120
+ scenario ".update" do
121
+ page.driver.put("/pizzas/0", @token_query)
122
+ page.should have_content "update"
123
+ end
124
+
125
+ scenario ".destroy" do
126
+ page.driver.delete("/pizzas/0", @token_query)
127
+ page.should have_content "destroy"
128
+ end
129
+
130
+ context "with token in the header" do
131
+ before { @headers = Hash["Authorization", "OAuth2 #{@token_value}"] }
132
+ before do
133
+ page.driver.browser.hacked_env.merge!(@headers)
134
+ end
135
+
136
+ scenario ".index" do
137
+ visit "/pizzas"
138
+ page.should have_content "index"
139
+ end
140
+ end
141
+ end
142
+
143
+ end
@@ -0,0 +1,227 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/acceptance_helper')
2
+
3
+ feature "ScopesController" do
4
+ before { host! "http://" + host }
5
+ before { @user = FactoryGirl.create(:user) }
6
+ before { @admin = FactoryGirl.create(:admin) }
7
+ before { @scope = FactoryGirl.create(:scope, values: ALL_SCOPE) }
8
+
9
+
10
+ context ".index" do
11
+ before { @uri = "/oauth/scopes" }
12
+ before { @read_scope = FactoryGirl.create(:scope, name: "read", values: READ_SCOPE) }
13
+
14
+ context "when not logged in" do
15
+ scenario "is not authorized" do
16
+ visit @uri
17
+ current_url.should == host + "/log_in"
18
+ end
19
+ end
20
+
21
+ context "when logged it" do
22
+ context "when admin" do
23
+ before { login(@admin) }
24
+
25
+ scenario "view the resources" do
26
+ visit @uri
27
+ should_visualize_scope(@scope)
28
+ should_visualize_scope(@read_scope)
29
+ end
30
+ end
31
+
32
+ context "when not admin" do
33
+ before { login(@user) }
34
+ scenario "do not list all resources" do
35
+ visit @uri
36
+ page.should have_content "Unauthorized access"
37
+ end
38
+ end
39
+ end
40
+ end
41
+
42
+
43
+ context ".show" do
44
+ before { @uri = "/oauth/scopes/" + @scope.id.as_json }
45
+
46
+ context "when not logged in" do
47
+ scenario "is not authorized" do
48
+ visit @uri
49
+ current_url.should == host + "/log_in"
50
+ end
51
+ end
52
+
53
+ context "when logged in" do
54
+ context "when admin" do
55
+ before { login(@admin) }
56
+
57
+ scenario "view a resource" do
58
+ visit @uri
59
+ should_visualize_scope(@scope)
60
+ end
61
+
62
+ scenario "resource not found" do
63
+ @scope.destroy
64
+ visit @uri
65
+ page.should have_content "Resource not found"
66
+ end
67
+
68
+ scenario "illegal id" do
69
+ visit "/oauth/scopes/0"
70
+ page.should have_content "Resource not found"
71
+ end
72
+ end
73
+
74
+ context "when not admin" do
75
+ before { login(@user) }
76
+ scenario "do not show a resource" do
77
+ visit @uri
78
+ page.should have_content "Unauthorized access"
79
+ end
80
+ end
81
+ end
82
+ end
83
+
84
+
85
+ context ".create" do
86
+ before { @uri = "/oauth/scopes/new" }
87
+
88
+ context "when not logged in" do
89
+ scenario "is not authorized" do
90
+ visit @uri
91
+ current_url.should == host + "/log_in"
92
+ end
93
+ end
94
+
95
+ context "when logged in" do
96
+ context "when admin" do
97
+ before { login(@admin) }
98
+
99
+ context "when valid" do
100
+ before do
101
+ visit @uri
102
+ fill_scope("pizza/read", "pizza/index pizza/show")
103
+ click_button 'Create Scope'
104
+ @scope = Oauth2Provider::Scope.last
105
+ end
106
+
107
+ scenario "create a resource" do
108
+ should_visualize_scope(@scope)
109
+ page.should have_content "was successfully created"
110
+ end
111
+
112
+ scenario "assign an URI to the resource" do
113
+ @scope.uri.should == host + "/oauth/scopes/" + @scope.id.as_json
114
+ end
115
+ end
116
+
117
+ context "when not valid" do
118
+ scenario "fails" do
119
+ visit @uri
120
+ fill_scope("", "")
121
+ click_button 'Create Scope'
122
+ page.should have_content "Name can't be blank"
123
+ page.should have_content "Values can't be blank"
124
+ end
125
+ end
126
+ end
127
+
128
+ context "when not admin" do
129
+ before { login(@user) }
130
+ scenario "do not create a resource" do
131
+ visit @uri
132
+ page.should have_content "Unauthorized access"
133
+ end
134
+ end
135
+ end
136
+ end
137
+
138
+ context ".update" do
139
+ before { @uri = "/oauth/scopes/" + @scope.id.as_json + "/edit" }
140
+
141
+ context "when not logged in" do
142
+ scenario "is not authorized" do
143
+ visit @uri
144
+ current_url.should == host + "/log_in"
145
+ end
146
+ end
147
+
148
+ context "when logged in" do
149
+ context "when admin" do
150
+ before { login(@admin) }
151
+
152
+ scenario "update a resource" do
153
+ visit @uri
154
+ fill_scope("pizza/read/toppings", "pizza/index pizza/show pizza/toppings")
155
+ click_button 'Update Scope'
156
+ page.should have_content("pizza/read/toppings")
157
+ page.should have_content("pizza/toppings")
158
+ end
159
+
160
+ scenario "resource not found" do
161
+ @scope.destroy
162
+ visit @uri
163
+ page.should have_content "Resource not found"
164
+ end
165
+
166
+ scenario "illegal id" do
167
+ visit "/oauth/scopes/0"
168
+ page.should have_content "Resource not found"
169
+ end
170
+
171
+ context "when not valid" do
172
+ scenario "fails" do
173
+ visit @uri
174
+ fill_scope("", "")
175
+ click_button 'Update Scope'
176
+ page.should have_content "Name can't be blank"
177
+ page.should have_content "Values can't be blank"
178
+ end
179
+ end
180
+
181
+ context "update clients'scopes" do
182
+
183
+ before do
184
+ Oauth2Provider::Scope.destroy_all
185
+ @scope = FactoryGirl.create(:scope_pizzas_all)
186
+ @scope_read = FactoryGirl.create(:scope_pizzas_read)
187
+ @client = FactoryGirl.create(:client)
188
+ @client_read = FactoryGirl.create(:client_read)
189
+ end
190
+
191
+ before do
192
+ visit "/oauth/scopes/" + @scope_read.id.as_json + "/edit"
193
+ fill_scope("pizzas/read", "pizzas/show")
194
+ click_button 'Update Scope'
195
+ end
196
+
197
+ context "with indirect client" do
198
+ subject { @client.reload.scope_values }
199
+ it { should_not include "pizzas/index" }
200
+ it { should include "pizzas/show" }
201
+ it { should include "pizzas/create" }
202
+ it { should include "pizzas/update" }
203
+ it { should include "pizzas/destroy" }
204
+ end
205
+
206
+ context "with direct client" do
207
+ subject { @client_read.reload.scope_values }
208
+ it { should_not include "pizzas/index" }
209
+ it { @client_read.reload.scope_values.should include "pizzas/show" }
210
+ end
211
+ end
212
+ end
213
+
214
+ context "when not admin" do
215
+ before { login(@user) }
216
+ scenario "do not update a resource" do
217
+ visit @uri
218
+ page.should have_content "Unauthorized access"
219
+ end
220
+ end
221
+ end
222
+ end
223
+
224
+ context ".destroy" do
225
+ end
226
+
227
+ end