Commit c43b289612b2420bc7e3c5faaf014b527ccace04
Exists in
master
and in
4 other branches
Merge branch '6-0-dev' of /home/git/repositories/gitlab/gitlabhq
Showing
639 changed files
with
7110 additions
and
9282 deletions
Show diff stats
Too many changes.
To preserve performance only 100 of 639 files displayed.
CHANGELOG
1 | +v 6.0.0 | |
2 | + - Epic: Replace teams with group membership | |
3 | + - Add project filter on dashboard | |
4 | + - cache project graph | |
5 | + - Drop support of root namespaces | |
6 | + - Redesign project settings navigation | |
7 | + - Restlyed login screen | |
8 | + - Default theme is classic now | |
9 | + - Cache result of methods like authorize_projects, project.team.members etc | |
10 | + - Remove $.ready events | |
11 | + - Fix onclick events being double binded | |
12 | + - Add notification level to group membership | |
13 | + - Move all project controllers/views under Projects:: module | |
14 | + - Move all profile controllers/views under Profiles:: module | |
15 | + - Redesign ssh keys page | |
16 | + - Generate fingerprint for ssh keys | |
17 | + - You an use arrows to navigate at tree view | |
18 | + - Apply user project limit only for personal projects | |
19 | + | |
1 | 20 | v 5.4.0 |
2 | 21 | - Ability to edit own comments |
3 | 22 | - Documentation improvements | ... | ... |
Capfile.example
Gemfile
... | ... | @@ -23,7 +23,7 @@ gem 'omniauth-github' |
23 | 23 | |
24 | 24 | # Extracting information from a git repository |
25 | 25 | # Provide access to Gitlab::Git library |
26 | -gem 'gitlab_git', '~> 1.3.0' | |
26 | +gem 'gitlab_git', '~> 1.4.1' | |
27 | 27 | |
28 | 28 | # Ruby/Rack Git Smart-HTTP Server Handler |
29 | 29 | gem 'gitlab-grack', '~> 1.0.1', require: 'grack' |
... | ... | @@ -35,7 +35,7 @@ gem 'gitlab_omniauth-ldap', '1.0.3', require: "omniauth-ldap" |
35 | 35 | gem "gitlab-pygments.rb", '~> 0.3.2', require: 'pygments.rb' |
36 | 36 | |
37 | 37 | # Git Wiki |
38 | -gem "gitlab-gollum-lib", "~> 1.0.0", require: 'gollum-lib' | |
38 | +gem "gitlab-gollum-lib", "~> 1.0.1", require: 'gollum-lib' | |
39 | 39 | |
40 | 40 | # Language detection |
41 | 41 | gem "github-linguist", require: "linguist" |
... | ... | @@ -173,7 +173,7 @@ group :development, :test do |
173 | 173 | gem 'factory_girl_rails' |
174 | 174 | |
175 | 175 | # Prevent occasions where minitest is not bundled in packaged versions of ruby (see #3826) |
176 | - gem 'minitest' | |
176 | + gem 'minitest', '~> 4.7.0' | |
177 | 177 | |
178 | 178 | # Generate Fake data |
179 | 179 | gem "ffaker" |
... | ... | @@ -203,5 +203,5 @@ group :test do |
203 | 203 | end |
204 | 204 | |
205 | 205 | group :production do |
206 | - gem "gitlab_meta", '5.0' | |
206 | + gem "gitlab_meta", '6.0' | |
207 | 207 | end | ... | ... |
Gemfile.lock
1 | 1 | GIT |
2 | 2 | remote: https://github.com/ctran/annotate_models.git |
3 | - revision: 8bd159c7a484093fde84beaa9e6398f25ddacf09 | |
3 | + revision: 18a4e2eb77c8f3ef695b563e4a7ca45dfede819b | |
4 | 4 | specs: |
5 | - annotate (2.6.0.beta1) | |
5 | + annotate (2.6.0.beta2) | |
6 | 6 | activerecord (>= 2.3.0) |
7 | 7 | rake (>= 0.8.7) |
8 | 8 | |
... | ... | @@ -42,20 +42,20 @@ GEM |
42 | 42 | activesupport (3.2.13) |
43 | 43 | i18n (= 0.6.1) |
44 | 44 | multi_json (~> 1.0) |
45 | - acts-as-taggable-on (2.4.0) | |
46 | - rails (~> 3.0) | |
45 | + acts-as-taggable-on (2.4.1) | |
46 | + rails (>= 3, < 5) | |
47 | 47 | addressable (2.3.4) |
48 | 48 | arel (3.0.2) |
49 | 49 | asciidoctor (0.1.3) |
50 | 50 | awesome_print (1.1.0) |
51 | - backports (2.6.7) | |
51 | + backports (3.3.2) | |
52 | 52 | bcrypt-ruby (3.0.1) |
53 | - better_errors (0.8.0) | |
53 | + better_errors (0.9.0) | |
54 | 54 | coderay (>= 1.0.0) |
55 | 55 | erubis (>= 2.6.6) |
56 | - binding_of_caller (0.7.1) | |
56 | + binding_of_caller (0.7.2) | |
57 | 57 | debug_inspector (>= 0.0.1) |
58 | - bootstrap-sass (2.3.1.0) | |
58 | + bootstrap-sass (2.3.2.0) | |
59 | 59 | sass (~> 3.2) |
60 | 60 | builder (3.0.4) |
61 | 61 | capybara (2.1.0) |
... | ... | @@ -67,7 +67,7 @@ GEM |
67 | 67 | carrierwave (0.8.0) |
68 | 68 | activemodel (>= 3.2.0) |
69 | 69 | activesupport (>= 3.2.0) |
70 | - celluloid (0.14.0) | |
70 | + celluloid (0.14.1) | |
71 | 71 | timers (>= 1.0.0) |
72 | 72 | charlock_holmes (0.6.9.4) |
73 | 73 | childprocess (0.3.9) |
... | ... | @@ -75,7 +75,7 @@ GEM |
75 | 75 | chosen-rails (0.9.8) |
76 | 76 | railties (~> 3.0) |
77 | 77 | thor (~> 0.14) |
78 | - code_analyzer (0.3.1) | |
78 | + code_analyzer (0.3.2) | |
79 | 79 | sexp_processor |
80 | 80 | coderay (1.0.9) |
81 | 81 | coffee-rails (3.2.2) |
... | ... | @@ -87,15 +87,16 @@ GEM |
87 | 87 | coffee-script-source (1.6.2) |
88 | 88 | colored (1.2) |
89 | 89 | colorize (0.5.8) |
90 | - connection_pool (1.0.0) | |
90 | + connection_pool (1.1.0) | |
91 | 91 | coveralls (0.6.7) |
92 | 92 | colorize |
93 | 93 | multi_json (~> 1.3) |
94 | 94 | rest-client |
95 | 95 | simplecov (>= 0.7) |
96 | 96 | thor |
97 | - crack (0.3.2) | |
98 | - d3_rails (3.1.4) | |
97 | + crack (0.4.0) | |
98 | + safe_yaml (~> 0.9.0) | |
99 | + d3_rails (3.1.10) | |
99 | 100 | railties (>= 3.1.0) |
100 | 101 | daemons (1.1.9) |
101 | 102 | database_cleaner (1.0.1) |
... | ... | @@ -107,11 +108,11 @@ GEM |
107 | 108 | railties (~> 3.1) |
108 | 109 | warden (~> 1.2.1) |
109 | 110 | diff-lcs (1.2.4) |
110 | - dotenv (0.7.0) | |
111 | + dotenv (0.8.0) | |
111 | 112 | email_spec (1.4.0) |
112 | 113 | launchy (~> 2.1) |
113 | 114 | mail (~> 2.2) |
114 | - enumerize (0.5.1) | |
115 | + enumerize (0.6.1) | |
115 | 116 | activesupport (>= 3.2) |
116 | 117 | erubis (2.7.0) |
117 | 118 | escape_utils (0.2.4) |
... | ... | @@ -130,8 +131,8 @@ GEM |
130 | 131 | faraday (>= 0.7.4, < 0.9) |
131 | 132 | faye-websocket (0.4.7) |
132 | 133 | eventmachine (>= 0.12.0) |
133 | - ffaker (1.16.0) | |
134 | - ffi (1.8.1) | |
134 | + ffaker (1.16.1) | |
135 | + ffi (1.9.0) | |
135 | 136 | fog (1.3.1) |
136 | 137 | builder |
137 | 138 | excon (~> 0.13.0) |
... | ... | @@ -157,17 +158,17 @@ GEM |
157 | 158 | pygments.rb (>= 0.2.13) |
158 | 159 | github-markdown (0.5.3) |
159 | 160 | github-markup (0.7.5) |
160 | - gitlab-gollum-lib (1.0.0) | |
161 | + gitlab-gollum-lib (1.0.1) | |
161 | 162 | github-markdown (~> 0.5.3) |
162 | 163 | github-markup (>= 0.7.5, < 1.0.0) |
163 | - gitlab-grit (~> 2.5.1) | |
164 | + gitlab-grit (>= 2.5.1) | |
164 | 165 | nokogiri (~> 1.5.9) |
165 | 166 | pygments.rb (~> 0.4.2) |
166 | 167 | sanitize (~> 2.0.3) |
167 | 168 | stringex (~> 1.5.1) |
168 | 169 | gitlab-grack (1.0.1) |
169 | 170 | rack (~> 1.4.1) |
170 | - gitlab-grit (2.5.1) | |
171 | + gitlab-grit (2.6.0) | |
171 | 172 | charlock_holmes (~> 0.6.9) |
172 | 173 | diff-lcs (~> 1.1) |
173 | 174 | mime-types (~> 1.15) |
... | ... | @@ -175,17 +176,17 @@ GEM |
175 | 176 | gitlab-pygments.rb (0.3.2) |
176 | 177 | posix-spawn (~> 0.3.6) |
177 | 178 | yajl-ruby (~> 1.1.0) |
178 | - gitlab_git (1.3.0) | |
179 | + gitlab_git (1.4.1) | |
179 | 180 | activesupport (~> 3.2.13) |
180 | 181 | github-linguist (~> 2.3.4) |
181 | - gitlab-grit (~> 2.5.1) | |
182 | - gitlab_meta (5.0) | |
182 | + gitlab-grit (~> 2.6.0) | |
183 | + gitlab_meta (6.0) | |
183 | 184 | gitlab_omniauth-ldap (1.0.3) |
184 | 185 | net-ldap (~> 0.3.1) |
185 | 186 | omniauth (~> 1.0) |
186 | 187 | pyu-ruby-sasl (~> 0.0.3.1) |
187 | 188 | rubyntlm (~> 0.1.1) |
188 | - gon (4.1.0) | |
189 | + gon (4.1.1) | |
189 | 190 | actionpack (>= 2.3.0) |
190 | 191 | json |
191 | 192 | grape (0.4.1) |
... | ... | @@ -202,19 +203,19 @@ GEM |
202 | 203 | activesupport |
203 | 204 | multi_json (>= 1.3.2) |
204 | 205 | growl (1.0.3) |
205 | - guard (1.8.0) | |
206 | + guard (1.8.1) | |
206 | 207 | formatador (>= 0.2.4) |
207 | 208 | listen (>= 1.0.0) |
208 | 209 | lumberjack (>= 1.0.2) |
209 | 210 | pry (>= 0.9.10) |
210 | 211 | thor (>= 0.14.6) |
211 | - guard-rspec (3.0.0) | |
212 | + guard-rspec (3.0.2) | |
212 | 213 | guard (>= 1.8) |
213 | 214 | rspec (~> 2.13) |
214 | 215 | guard-spinach (0.0.2) |
215 | 216 | guard (>= 1.1) |
216 | 217 | spinach |
217 | - haml (4.0.2) | |
218 | + haml (4.0.3) | |
218 | 219 | tilt |
219 | 220 | haml-rails (0.4) |
220 | 221 | actionpack (>= 3.1, < 4.1) |
... | ... | @@ -222,9 +223,10 @@ GEM |
222 | 223 | haml (>= 3.1, < 4.1) |
223 | 224 | railties (>= 3.1, < 4.1) |
224 | 225 | hashie (1.2.0) |
225 | - hike (1.2.2) | |
226 | + hike (1.2.3) | |
226 | 227 | hipchat (0.9.0) |
227 | 228 | httparty |
229 | + httparty | |
228 | 230 | http_parser.rb (0.5.3) |
229 | 231 | httparty (0.11.0) |
230 | 232 | multi_json (~> 1.0) |
... | ... | @@ -255,18 +257,17 @@ GEM |
255 | 257 | actionpack (>= 3.0.0) |
256 | 258 | activesupport (>= 3.0.0) |
257 | 259 | kgio (2.8.0) |
258 | - launchy (2.2.0) | |
260 | + launchy (2.3.0) | |
259 | 261 | addressable (~> 2.3) |
260 | - letter_opener (1.1.0) | |
261 | - launchy (~> 2.2.0) | |
262 | + letter_opener (1.1.1) | |
263 | + launchy (~> 2.2) | |
262 | 264 | libv8 (3.11.8.17) |
263 | - listen (1.1.3) | |
265 | + listen (1.2.2) | |
264 | 266 | rb-fsevent (>= 0.9.3) |
265 | 267 | rb-inotify (>= 0.9) |
266 | 268 | rb-kqueue (>= 0.2) |
267 | 269 | lumberjack (1.0.3) |
268 | - mail (2.5.3) | |
269 | - i18n (>= 0.4.0) | |
270 | + mail (2.5.4) | |
270 | 271 | mime-types (~> 1.16) |
271 | 272 | treetop (~> 1.4.8) |
272 | 273 | method_source (0.8.1) |
... | ... | @@ -274,15 +275,15 @@ GEM |
274 | 275 | minitest (4.7.4) |
275 | 276 | modernizr (2.6.2) |
276 | 277 | sprockets (~> 2.0) |
277 | - multi_json (1.7.3) | |
278 | - multi_xml (0.5.3) | |
278 | + multi_json (1.7.7) | |
279 | + multi_xml (0.5.4) | |
279 | 280 | multipart-post (1.2.0) |
280 | 281 | mysql2 (0.3.11) |
281 | 282 | net-ldap (0.3.1) |
282 | 283 | net-scp (1.0.4) |
283 | 284 | net-ssh (>= 1.99.1) |
284 | 285 | net-ssh (2.6.8) |
285 | - nokogiri (1.5.9) | |
286 | + nokogiri (1.5.10) | |
286 | 287 | oauth (0.4.7) |
287 | 288 | oauth2 (0.8.1) |
288 | 289 | faraday (~> 0.8) |
... | ... | @@ -296,7 +297,7 @@ GEM |
296 | 297 | omniauth-github (1.1.0) |
297 | 298 | omniauth (~> 1.0) |
298 | 299 | omniauth-oauth2 (~> 1.1) |
299 | - omniauth-google-oauth2 (0.1.17) | |
300 | + omniauth-google-oauth2 (0.1.19) | |
300 | 301 | omniauth (~> 1.0) |
301 | 302 | omniauth-oauth2 |
302 | 303 | omniauth-oauth (1.0.1) |
... | ... | @@ -305,7 +306,7 @@ GEM |
305 | 306 | omniauth-oauth2 (1.1.1) |
306 | 307 | oauth2 (~> 0.8.0) |
307 | 308 | omniauth (~> 1.0) |
308 | - omniauth-twitter (0.0.16) | |
309 | + omniauth-twitter (0.0.17) | |
309 | 310 | multi_json (~> 1.3) |
310 | 311 | omniauth-oauth (~> 1.0) |
311 | 312 | orm_adapter (0.4.0) |
... | ... | @@ -354,7 +355,7 @@ GEM |
354 | 355 | rails-dev-tweaks (0.6.1) |
355 | 356 | actionpack (~> 3.1) |
356 | 357 | railties (~> 3.1) |
357 | - rails_best_practices (1.13.4) | |
358 | + rails_best_practices (1.13.8) | |
358 | 359 | activesupport |
359 | 360 | awesome_print |
360 | 361 | code_analyzer |
... | ... | @@ -370,7 +371,7 @@ GEM |
370 | 371 | rdoc (~> 3.4) |
371 | 372 | thor (>= 0.14.6, < 2.0) |
372 | 373 | raindrops (0.11.0) |
373 | - rake (10.0.4) | |
374 | + rake (10.1.0) | |
374 | 375 | rb-fsevent (0.9.3) |
375 | 376 | rb-inotify (0.9.0) |
376 | 377 | ffi (>= 0.5.0) |
... | ... | @@ -398,7 +399,7 @@ GEM |
398 | 399 | redis-store (~> 1.1.0) |
399 | 400 | redis-store (1.1.3) |
400 | 401 | redis (>= 2.2.0) |
401 | - ref (1.0.4) | |
402 | + ref (1.0.5) | |
402 | 403 | rest-client (1.6.7) |
403 | 404 | mime-types (>= 1.16) |
404 | 405 | rspec (2.13.0) |
... | ... | @@ -409,7 +410,7 @@ GEM |
409 | 410 | rspec-expectations (2.13.0) |
410 | 411 | diff-lcs (>= 1.1.3, < 2.0) |
411 | 412 | rspec-mocks (2.13.1) |
412 | - rspec-rails (2.13.1) | |
413 | + rspec-rails (2.13.2) | |
413 | 414 | actionpack (>= 3.0) |
414 | 415 | activesupport (>= 3.0) |
415 | 416 | railties (>= 3.0) |
... | ... | @@ -417,9 +418,10 @@ GEM |
417 | 418 | rspec-expectations (~> 2.13.0) |
418 | 419 | rspec-mocks (~> 2.13.0) |
419 | 420 | ruby-hmac (0.4.0) |
420 | - ruby-progressbar (1.0.2) | |
421 | + ruby-progressbar (1.1.1) | |
421 | 422 | rubyntlm (0.1.1) |
422 | 423 | rubyzip (0.9.9) |
424 | + safe_yaml (0.9.3) | |
423 | 425 | sanitize (2.0.3) |
424 | 426 | nokogiri (>= 1.4.4, < 1.6) |
425 | 427 | sass (3.2.9) |
... | ... | @@ -433,10 +435,10 @@ GEM |
433 | 435 | seed-fu (2.2.0) |
434 | 436 | activerecord (~> 3.1) |
435 | 437 | activesupport (~> 3.1) |
436 | - select2-rails (3.3.1) | |
437 | - sass-rails (>= 3.2) | |
438 | + select2-rails (3.4.2) | |
439 | + sass-rails | |
438 | 440 | thor (~> 0.14) |
439 | - selenium-webdriver (2.32.1) | |
441 | + selenium-webdriver (2.33.0) | |
440 | 442 | childprocess (>= 0.2.5) |
441 | 443 | multi_json (~> 1.0) |
442 | 444 | rubyzip |
... | ... | @@ -445,8 +447,8 @@ GEM |
445 | 447 | sexp_processor (4.2.1) |
446 | 448 | shoulda-matchers (2.1.0) |
447 | 449 | activesupport (>= 3.0.0) |
448 | - sidekiq (2.12.0) | |
449 | - celluloid (>= 0.14.0) | |
450 | + sidekiq (2.12.4) | |
451 | + celluloid (>= 0.14.1) | |
450 | 452 | connection_pool (>= 1.0.0) |
451 | 453 | json |
452 | 454 | redis (>= 3.0) |
... | ... | @@ -456,23 +458,23 @@ GEM |
456 | 458 | multi_json (~> 1.0) |
457 | 459 | simplecov-html (~> 0.7.1) |
458 | 460 | simplecov-html (0.7.1) |
459 | - sinatra (1.3.6) | |
461 | + sinatra (1.4.3) | |
460 | 462 | rack (~> 1.4) |
461 | - rack-protection (~> 1.3) | |
462 | - tilt (~> 1.3, >= 1.3.3) | |
463 | + rack-protection (~> 1.4) | |
464 | + tilt (~> 1.3, >= 1.3.4) | |
463 | 465 | six (0.2.0) |
464 | - slim (1.3.8) | |
465 | - temple (~> 0.6.3) | |
466 | - tilt (~> 1.3.3) | |
466 | + slim (2.0.0) | |
467 | + temple (~> 0.6.5) | |
468 | + tilt (~> 1.3, >= 1.3.3) | |
467 | 469 | slop (3.4.5) |
468 | - spinach (0.8.2) | |
470 | + spinach (0.8.3) | |
469 | 471 | colorize (= 0.5.8) |
470 | 472 | gherkin-ruby (~> 0.3.0) |
471 | 473 | spinach-rails (0.2.1) |
472 | 474 | capybara (>= 2.0.0) |
473 | 475 | railties (>= 3) |
474 | 476 | spinach (>= 0.4) |
475 | - spork (1.0.0rc3) | |
477 | + spork (1.0.0rc2) | |
476 | 478 | sprockets (2.2.2) |
477 | 479 | hike (~> 1.2) |
478 | 480 | multi_json (~> 1.0) |
... | ... | @@ -481,7 +483,7 @@ GEM |
481 | 483 | stamp (0.5.0) |
482 | 484 | state_machine (1.2.0) |
483 | 485 | stringex (1.5.1) |
484 | - temple (0.6.4) | |
486 | + temple (0.6.5) | |
485 | 487 | test_after_commit (0.2.0) |
486 | 488 | therubyracer (0.11.4) |
487 | 489 | libv8 (~> 3.11.8.12) |
... | ... | @@ -491,7 +493,7 @@ GEM |
491 | 493 | eventmachine (>= 0.12.6) |
492 | 494 | rack (>= 1.0.0) |
493 | 495 | thor (0.18.1) |
494 | - tilt (1.3.7) | |
496 | + tilt (1.4.1) | |
495 | 497 | timers (1.1.0) |
496 | 498 | tinder (1.9.2) |
497 | 499 | eventmachine (~> 1.0) |
... | ... | @@ -502,17 +504,17 @@ GEM |
502 | 504 | mime-types (~> 1.19) |
503 | 505 | multi_json (~> 1.5) |
504 | 506 | twitter-stream (~> 0.1) |
505 | - treetop (1.4.12) | |
507 | + treetop (1.4.14) | |
506 | 508 | polyglot |
507 | 509 | polyglot (>= 0.3.1) |
508 | - turbolinks (1.1.1) | |
510 | + turbolinks (1.2.0) | |
509 | 511 | coffee-rails |
510 | 512 | twitter-stream (0.1.16) |
511 | 513 | eventmachine (>= 0.12.8) |
512 | 514 | http_parser.rb (~> 0.5.1) |
513 | 515 | simple_oauth (~> 0.1.4) |
514 | 516 | tzinfo (0.3.37) |
515 | - uglifier (2.0.1) | |
517 | + uglifier (2.1.1) | |
516 | 518 | execjs (>= 0.3.0) |
517 | 519 | multi_json (~> 1.0, >= 1.0.2) |
518 | 520 | underscore-rails (1.4.4) |
... | ... | @@ -520,8 +522,8 @@ GEM |
520 | 522 | kgio (~> 2.6) |
521 | 523 | rack |
522 | 524 | raindrops (~> 0.7) |
523 | - virtus (0.5.4) | |
524 | - backports (~> 2.6.1) | |
525 | + virtus (0.5.5) | |
526 | + backports (~> 3.3) | |
525 | 527 | descendants_tracker (~> 0.0.1) |
526 | 528 | warden (1.2.1) |
527 | 529 | rack (>= 1.0) |
... | ... | @@ -563,11 +565,11 @@ DEPENDENCIES |
563 | 565 | gemoji (~> 1.2.1) |
564 | 566 | github-linguist |
565 | 567 | github-markup (~> 0.7.4) |
566 | - gitlab-gollum-lib (~> 1.0.0) | |
568 | + gitlab-gollum-lib (~> 1.0.1) | |
567 | 569 | gitlab-grack (~> 1.0.1) |
568 | 570 | gitlab-pygments.rb (~> 0.3.2) |
569 | - gitlab_git (~> 1.3.0) | |
570 | - gitlab_meta (= 5.0) | |
571 | + gitlab_git (~> 1.4.1) | |
572 | + gitlab_meta (= 6.0) | |
571 | 573 | gitlab_omniauth-ldap (= 1.0.3) |
572 | 574 | gon |
573 | 575 | grape (~> 0.4.1) |
... | ... | @@ -586,7 +588,7 @@ DEPENDENCIES |
586 | 588 | kaminari (~> 0.14.1) |
587 | 589 | launchy |
588 | 590 | letter_opener |
589 | - minitest | |
591 | + minitest (~> 4.7.0) | |
590 | 592 | modernizr (= 2.6.2) |
591 | 593 | mysql2 |
592 | 594 | omniauth (~> 1.1.3) | ... | ... |
Procfile
VERSION
app/assets/images/login-logo.png
... | ... | @@ -0,0 +1,24 @@ |
1 | +class BlobView | |
2 | + constructor: -> | |
3 | + # See if there are lines selected | |
4 | + # "#L12" and "#L34-56" supported | |
5 | + highlightBlobLines = -> | |
6 | + if window.location.hash isnt "" | |
7 | + matches = window.location.hash.match(/\#L(\d+)(\-(\d+))?/) | |
8 | + first_line = parseInt(matches?[1]) | |
9 | + last_line = parseInt(matches?[3]) | |
10 | + | |
11 | + unless isNaN first_line | |
12 | + last_line = first_line if isNaN(last_line) | |
13 | + $("#tree-content-holder .highlight .line").removeClass("hll") | |
14 | + $("#LC#{line}").addClass("hll") for line in [first_line..last_line] | |
15 | + $("#L#{first_line}").ScrollTo() | |
16 | + | |
17 | + # Highlight the correct lines on load | |
18 | + highlightBlobLines() | |
19 | + | |
20 | + # Highlight the correct lines when the hash part of the URL changes | |
21 | + $(window).on 'hashchange', highlightBlobLines | |
22 | + | |
23 | + | |
24 | +@BlobView = BlobView | ... | ... |
app/assets/javascripts/dashboard.js.coffee
... | ... | @@ -8,6 +8,22 @@ class Dashboard |
8 | 8 | @toggleFilter($(event.currentTarget)) |
9 | 9 | @reloadActivities() |
10 | 10 | |
11 | + $(".dash-filter").keyup -> | |
12 | + terms = $(this).val() | |
13 | + uiBox = $(this).parents('.ui-box').first() | |
14 | + if terms == "" || terms == undefined | |
15 | + uiBox.find(".dash-list li").show() | |
16 | + else | |
17 | + uiBox.find(".dash-list li").each (index) -> | |
18 | + name = $(this).find(".well-title").text() | |
19 | + | |
20 | + if name.toLowerCase().search(terms.toLowerCase()) == -1 | |
21 | + $(this).hide() | |
22 | + else | |
23 | + $(this).show() | |
24 | + | |
25 | + | |
26 | + | |
11 | 27 | reloadActivities: -> |
12 | 28 | $(".content_list").html '' |
13 | 29 | Pager.init 20, true | ... | ... |
app/assets/javascripts/dispatcher.js.coffee
... | ... | @@ -16,20 +16,26 @@ class Dispatcher |
16 | 16 | path = page.split(':') |
17 | 17 | |
18 | 18 | switch page |
19 | - when 'issues:index' | |
19 | + when 'projects:issues:index' | |
20 | 20 | Issues.init() |
21 | 21 | when 'dashboard:show' |
22 | 22 | new Dashboard() |
23 | - when 'commit:show' | |
23 | + when 'projects:commit:show' | |
24 | 24 | new Commit() |
25 | - when 'groups:show', 'teams:show', 'projects:show' | |
25 | + when 'groups:show', 'projects:show' | |
26 | 26 | Pager.init(20, true) |
27 | 27 | when 'projects:new', 'projects:edit' |
28 | 28 | new Project() |
29 | - when 'walls:show' | |
29 | + when 'projects:walls:show' | |
30 | 30 | new Wall(project_id) |
31 | - when 'teams:members:index' | |
31 | + when 'projects:teams:members:index' | |
32 | 32 | new TeamMembers() |
33 | + when 'groups:people' | |
34 | + new GroupMembers() | |
35 | + when 'projects:tree:show' | |
36 | + new TreeView() | |
37 | + when 'projects:blob:show' | |
38 | + new BlobView() | |
33 | 39 | |
34 | 40 | switch path.first() |
35 | 41 | when 'admin' then new Admin() | ... | ... |
app/assets/javascripts/main.js.coffee
... | ... | @@ -50,11 +50,12 @@ window.startSpinner = -> |
50 | 50 | window.stopSpinner = -> |
51 | 51 | $('.turbolink-spinner').fadeOut() |
52 | 52 | |
53 | -window.stopEndlessScroll = -> | |
53 | +window.unbindEvents = -> | |
54 | 54 | $(document).unbind('scroll') |
55 | + $(document).off('scroll') | |
55 | 56 | |
56 | 57 | document.addEventListener("page:fetch", startSpinner) |
57 | -document.addEventListener("page:fetch", stopEndlessScroll) | |
58 | +document.addEventListener("page:fetch", unbindEvents) | |
58 | 59 | document.addEventListener("page:receive", stopSpinner) |
59 | 60 | |
60 | 61 | $ -> |
... | ... | @@ -66,7 +67,6 @@ $ -> |
66 | 67 | $('.appear-data').fadeIn() |
67 | 68 | e.preventDefault() |
68 | 69 | |
69 | - | |
70 | 70 | # Initialize chosen selects |
71 | 71 | $('select.chosen').chosen() |
72 | 72 | |
... | ... | @@ -110,6 +110,10 @@ $ -> |
110 | 110 | when 115 |
111 | 111 | $("#search").focus() |
112 | 112 | e.preventDefault() |
113 | + when 63 | |
114 | + new Shortcuts() | |
115 | + e.preventDefault() | |
116 | + | |
113 | 117 | |
114 | 118 | # Commit show suppressed diff |
115 | 119 | $(".supp_diff_link").bind "click", -> | ... | ... |
app/assets/javascripts/notes.js
1 | 1 | var NoteList = { |
2 | - | |
2 | + id: null, | |
3 | 3 | notes_path: null, |
4 | 4 | target_params: null, |
5 | 5 | target_id: 0, |
... | ... | @@ -16,6 +16,22 @@ var NoteList = { |
16 | 16 | // get initial set of notes |
17 | 17 | NoteList.getContent(); |
18 | 18 | |
19 | + // Unbind events to prevent firing twice | |
20 | + $(document).off("click", ".js-add-diff-note-button"); | |
21 | + $(document).off("click", ".js-discussion-reply-button"); | |
22 | + $(document).off("click", ".js-note-preview-button"); | |
23 | + $(document).off("click", ".js-note-attachment-input"); | |
24 | + $(document).off("click", ".js-close-discussion-note-form"); | |
25 | + $(document).off("click", ".js-note-delete"); | |
26 | + $(document).off("click", ".js-note-edit"); | |
27 | + $(document).off("click", ".js-note-edit-cancel"); | |
28 | + $(document).off("click", ".js-note-attachment-delete"); | |
29 | + $(document).off("click", ".js-choose-note-attachment-button"); | |
30 | + $(document).off("click", ".js-show-outdated-discussion"); | |
31 | + | |
32 | + $(document).off("ajax:complete", ".js-main-target-form"); | |
33 | + | |
34 | + | |
19 | 35 | // add a new diff note |
20 | 36 | $(document).on("click", |
21 | 37 | ".js-add-diff-note-button", | ... | ... |
app/assets/javascripts/stat_graph_contributors.js.coffee
... | ... | @@ -12,14 +12,35 @@ class window.ContributorsStatGraph |
12 | 12 | @master_graph.draw() |
13 | 13 | add_authors_graph: (author_data) -> |
14 | 14 | @authors = [] |
15 | - _.each(author_data, (d) => | |
15 | + limited_author_data = author_data.slice(0, 100) | |
16 | + _.each(limited_author_data, (d) => | |
16 | 17 | author_header = @create_author_header(d) |
17 | 18 | $(".contributors-list").append(author_header) |
18 | 19 | @authors[d.author] = author_graph = new ContributorsAuthorGraph(d.dates) |
19 | 20 | author_graph.draw() |
20 | 21 | ) |
21 | 22 | format_author_commit_info: (author) -> |
22 | - author.commits + " commits " + author.additions + " ++ / " + author.deletions + " --" | |
23 | + commits = $('<span/>', { | |
24 | + class: 'graph-author-commits-count' | |
25 | + }) | |
26 | + commits.text(author.commits + " commits") | |
27 | + | |
28 | + additions = $('<span/>', { | |
29 | + class: 'graph-additions' | |
30 | + }) | |
31 | + additions.text(author.additions + " ++") | |
32 | + | |
33 | + deletions = $('<span/>', { | |
34 | + class: 'graph-deletions' | |
35 | + }) | |
36 | + deletions.text(author.deletions + " --") | |
37 | + | |
38 | + $('<span/>').append(commits) | |
39 | + .append(" / ") | |
40 | + .append(additions) | |
41 | + .append(" / ") | |
42 | + .append(deletions) | |
43 | + | |
23 | 44 | create_author_header: (author) -> |
24 | 45 | list_item = $('<li/>', { |
25 | 46 | class: 'person' |
... | ... | @@ -30,7 +51,7 @@ class window.ContributorsStatGraph |
30 | 51 | class: 'commits' |
31 | 52 | }) |
32 | 53 | author_commit_info = @format_author_commit_info(author) |
33 | - author_commit_info_span.text(author_commit_info) | |
54 | + author_commit_info_span.html(author_commit_info) | |
34 | 55 | list_item.append(author_name) |
35 | 56 | list_item.append(author_commit_info_span) |
36 | 57 | list_item |
... | ... | @@ -52,10 +73,10 @@ class window.ContributorsStatGraph |
52 | 73 | @field = field |
53 | 74 | change_date_header: -> |
54 | 75 | x_domain = ContributorsGraph.prototype.x_domain |
55 | - print_date_format = d3.time.format("%B %e %Y"); | |
56 | - print = print_date_format(x_domain[0]) + " - " + print_date_format(x_domain[1]); | |
57 | - $("#date_header").text(print); | |
76 | + print_date_format = d3.time.format("%B %e %Y") | |
77 | + print = print_date_format(x_domain[0]) + " - " + print_date_format(x_domain[1]) | |
78 | + $("#date_header").text(print) | |
58 | 79 | redraw_author_commit_info: (author) -> |
59 | 80 | author_list_item = $(@authors[author.author].list_item) |
60 | 81 | author_commit_info = @format_author_commit_info(author) |
61 | - author_list_item.find("span").text(author_commit_info) | |
62 | 82 | \ No newline at end of file |
83 | + author_list_item.find("span").html(author_commit_info) | ... | ... |
app/assets/javascripts/stat_graph_contributors_graph.js.coffee
... | ... | @@ -71,7 +71,7 @@ class window.ContributorsMasterGraph extends ContributorsGraph |
71 | 71 | super @width, @height |
72 | 72 | create_axes: -> |
73 | 73 | @x_axis = d3.svg.axis().scale(@x).orient("bottom") |
74 | - @y_axis = d3.svg.axis().scale(@y).orient("left") | |
74 | + @y_axis = d3.svg.axis().scale(@y).orient("left").ticks(5) | |
75 | 75 | create_svg: -> |
76 | 76 | @svg = d3.select("#contributors-master").append("svg") |
77 | 77 | .attr("width", @width + @MARGIN.left + @MARGIN.right) |
... | ... | @@ -130,8 +130,8 @@ class window.ContributorsAuthorGraph extends ContributorsGraph |
130 | 130 | create_scale: -> |
131 | 131 | super @width, @height |
132 | 132 | create_axes: -> |
133 | - @x_axis = d3.svg.axis().scale(@x).orient("bottom").tickFormat(d3.time.format("%m/%d")); | |
134 | - @y_axis = d3.svg.axis().scale(@y).orient("left") | |
133 | + @x_axis = d3.svg.axis().scale(@x).orient("bottom").ticks(8) | |
134 | + @y_axis = d3.svg.axis().scale(@y).orient("left").ticks(5) | |
135 | 135 | create_area: (x, y) -> |
136 | 136 | @area = d3.svg.area().x((d) -> |
137 | 137 | parseDate = d3.time.format("%Y-%m-%d").parse |
... | ... | @@ -148,7 +148,7 @@ class window.ContributorsAuthorGraph extends ContributorsGraph |
148 | 148 | .append("g") |
149 | 149 | .attr("transform", "translate(" + @MARGIN.left + "," + @MARGIN.top + ")") |
150 | 150 | draw_path: (data) -> |
151 | - @svg.append("path").datum(data).attr("class", "area-contributor").attr("d", @area); | |
151 | + @svg.append("path").datum(data).attr("class", "area-contributor").attr("d", @area) | |
152 | 152 | draw: -> |
153 | 153 | @create_scale() |
154 | 154 | @create_axes() | ... | ... |
app/assets/javascripts/tree.js.coffee
1 | -# Code browser tree slider | |
2 | -# Make the entire tree-item row clickable, but not if clicking another link (like a commit message) | |
3 | -$(".tree-content-holder .tree-item").live 'click', (e) -> | |
4 | - if (e.target.nodeName != "A") | |
5 | - path = $('.tree-item-file-name a', this).attr('href') | |
6 | - Turbolinks.visit(path) | |
1 | +class TreeView | |
2 | + constructor: -> | |
3 | + @initKeyNav() | |
7 | 4 | |
8 | -$ -> | |
9 | - # Show the "Loading commit data" for only the first element | |
10 | - $('span.log_loading:first').removeClass('hide') | |
5 | + # Code browser tree slider | |
6 | + # Make the entire tree-item row clickable, but not if clicking another link (like a commit message) | |
7 | + $(".tree-content-holder .tree-item").on 'click', (e) -> | |
8 | + if (e.target.nodeName != "A") | |
9 | + path = $('.tree-item-file-name a', this).attr('href') | |
10 | + Turbolinks.visit(path) | |
11 | 11 | |
12 | - # See if there are lines selected | |
13 | - # "#L12" and "#L34-56" supported | |
14 | - highlightBlobLines = -> | |
15 | - if window.location.hash isnt "" | |
16 | - matches = window.location.hash.match(/\#L(\d+)(\-(\d+))?/) | |
17 | - first_line = parseInt(matches?[1]) | |
18 | - last_line = parseInt(matches?[3]) | |
12 | + # Show the "Loading commit data" for only the first element | |
13 | + $('span.log_loading:first').removeClass('hide') | |
19 | 14 | |
20 | - unless isNaN first_line | |
21 | - last_line = first_line if isNaN(last_line) | |
22 | - $("#tree-content-holder .highlight .line").removeClass("hll") | |
23 | - $("#LC#{line}").addClass("hll") for line in [first_line..last_line] | |
24 | - $("#L#{first_line}").ScrollTo() | |
15 | + initKeyNav: -> | |
16 | + li = $("tr.tree-item") | |
17 | + liSelected = null | |
18 | + $('body').keydown (e) -> | |
19 | + if e.which is 40 | |
20 | + if liSelected | |
21 | + next = liSelected.next() | |
22 | + if next.length > 0 | |
23 | + liSelected.removeClass "selected" | |
24 | + liSelected = next.addClass("selected") | |
25 | + else | |
26 | + liSelected = li.eq(0).addClass("selected") | |
25 | 27 | |
26 | - # Highlight the correct lines on load | |
27 | - highlightBlobLines() | |
28 | - # Highlight the correct lines when the hash part of the URL changes | |
29 | - $(window).on 'hashchange', highlightBlobLines | |
28 | + $(liSelected).focus() | |
29 | + else if e.which is 38 | |
30 | + if liSelected | |
31 | + next = liSelected.prev() | |
32 | + if next.length > 0 | |
33 | + liSelected.removeClass "selected" | |
34 | + liSelected = next.addClass("selected") | |
35 | + else | |
36 | + liSelected = li.last().addClass("selected") | |
37 | + | |
38 | + $(liSelected).focus() | |
39 | + else if e.which is 13 | |
40 | + path = $('.tree-item.selected .tree-item-file-name a').attr('href') | |
41 | + Turbolinks.visit(path) | |
42 | + | |
43 | +@TreeView = TreeView | ... | ... |
app/assets/stylesheets/common.scss
... | ... | @@ -206,17 +206,6 @@ p.time { |
206 | 206 | } |
207 | 207 | } |
208 | 208 | |
209 | -.arrow{ | |
210 | - background: #E3E5EA; | |
211 | - padding: 5px; | |
212 | - margin-top: 5px; | |
213 | - @include border-radius(5px); | |
214 | - text-shadow: none; | |
215 | - color: #999; | |
216 | - line-height: 16px; | |
217 | - font-weight: bold; | |
218 | -} | |
219 | - | |
220 | 209 | .thin_area{ |
221 | 210 | height: 150px; |
222 | 211 | } |
... | ... | @@ -311,14 +300,17 @@ li.note { |
311 | 300 | } |
312 | 301 | } |
313 | 302 | |
314 | -.error_message { | |
315 | - @extend .cred; | |
316 | - border-left: 4px solid #E99; | |
303 | +.error-message { | |
317 | 304 | padding: 10px; |
318 | - margin-bottom: 10px; | |
319 | - background: #FEE; | |
305 | + background: #C67; | |
320 | 306 | padding-left: 20px; |
307 | + margin: 0; | |
308 | + color: #FFF; | |
321 | 309 | |
310 | + a { | |
311 | + color: #fff; | |
312 | + text-decoration: underline; | |
313 | + } | |
322 | 314 | &.centered { |
323 | 315 | text-align: center; |
324 | 316 | } | ... | ... |
app/assets/stylesheets/gitlab_bootstrap/common.scss
app/assets/stylesheets/gitlab_bootstrap/lists.scss
app/assets/stylesheets/gitlab_bootstrap/nav.scss
app/assets/stylesheets/sections/dashboard.scss
... | ... | @@ -7,28 +7,13 @@ |
7 | 7 | @extend .pull-right; |
8 | 8 | |
9 | 9 | .ui-box { |
10 | - margin: 3px; | |
10 | + margin: 0px; | |
11 | + box-shadow: none; | |
12 | + | |
11 | 13 | > .title { |
12 | 14 | padding: 2px 15px; |
13 | 15 | } |
14 | 16 | .nav-projects-tabs li { padding: 0; } |
15 | - .well-list { | |
16 | - li { padding: 15px; } | |
17 | - .arrow { | |
18 | - float: right; | |
19 | - padding: 10px; | |
20 | - margin: 0; | |
21 | - } | |
22 | - .last_activity { | |
23 | - padding-top: 5px; | |
24 | - display: block; | |
25 | - span, strong { | |
26 | - font-size: 12px; | |
27 | - color: #666; | |
28 | - } | |
29 | - } | |
30 | - } | |
31 | - @extend .ui-box; | |
32 | 17 | } |
33 | 18 | } |
34 | 19 | } |
... | ... | @@ -46,3 +31,72 @@ |
46 | 31 | } |
47 | 32 | } |
48 | 33 | |
34 | +.dashboard { | |
35 | + .dash-filter { | |
36 | + margin: 0; | |
37 | + padding: 4px 6px; | |
38 | + width: 202px; | |
39 | + float: left; | |
40 | + margin-top: 3px; | |
41 | + margin-left: -2px; | |
42 | + } | |
43 | +} | |
44 | + | |
45 | +@media (max-width: 1200px) { | |
46 | + .dashboard .dash-filter { | |
47 | + width: 132px; | |
48 | + } | |
49 | +} | |
50 | + | |
51 | +.dash-sidebar-tabs { | |
52 | + margin-bottom: 2px; | |
53 | + border: none; | |
54 | + margin: 0; | |
55 | + | |
56 | + li { | |
57 | + &.active { | |
58 | + a { | |
59 | + @include linear-gradient(#f5f5f5, #eee); | |
60 | + border-bottom: 1px solid #EEE !important; | |
61 | + &:hover { | |
62 | + background: #eee; | |
63 | + } | |
64 | + } | |
65 | + } | |
66 | + | |
67 | + a { | |
68 | + border-color: #CCC !important; | |
69 | + } | |
70 | + } | |
71 | +} | |
72 | + | |
73 | +.project-row, .group-row { | |
74 | + padding: 15px !important; | |
75 | + | |
76 | + .namespace-name { | |
77 | + color: #666; | |
78 | + font-weight: bold; | |
79 | + } | |
80 | + | |
81 | + .project-name, .group-name { | |
82 | + font-size: 16px; | |
83 | + } | |
84 | + | |
85 | + | |
86 | + .arrow { | |
87 | + float: right; | |
88 | + padding: 10px 5px; | |
89 | + margin: 0; | |
90 | + font-size: 20px; | |
91 | + color: #666; | |
92 | + } | |
93 | + | |
94 | + .last-activity, .owner-info { | |
95 | + color: #AAA; | |
96 | + display: block; | |
97 | + margin-top: 5px; | |
98 | + .date, .owner { | |
99 | + color: #777; | |
100 | + } | |
101 | + } | |
102 | +} | ... | ... |
app/assets/stylesheets/sections/events.scss
... | ... | @@ -41,6 +41,8 @@ |
41 | 41 | } |
42 | 42 | } |
43 | 43 | .event-body { |
44 | + margin-left: 35px; | |
45 | + | |
44 | 46 | .commit p { |
45 | 47 | color: #666; |
46 | 48 | padding-top: 5px; |
... | ... | @@ -51,7 +53,6 @@ |
51 | 53 | .event-note { |
52 | 54 | color: #555; |
53 | 55 | margin-top: 5px; |
54 | - margin-left: 40px; | |
55 | 56 | |
56 | 57 | pre { |
57 | 58 | border: none; |
... | ... | @@ -77,10 +78,6 @@ |
77 | 78 | margin-right: 5px; |
78 | 79 | } |
79 | 80 | } |
80 | - .avatar { | |
81 | - position: relative; | |
82 | - top: -3px; | |
83 | - } | |
84 | 81 | .event_icon { |
85 | 82 | position: relative; |
86 | 83 | float: right; |
... | ... | @@ -95,11 +92,10 @@ |
95 | 92 | } |
96 | 93 | } |
97 | 94 | ul { |
98 | - margin-left: 50px; | |
99 | 95 | margin-bottom: 5px; |
100 | 96 | .avatar { |
101 | 97 | width: 18px; |
102 | - margin-top: 3px; | |
98 | + margin: 2px 4px; | |
103 | 99 | } |
104 | 100 | } |
105 | 101 | |
... | ... | @@ -118,7 +114,12 @@ |
118 | 114 | } |
119 | 115 | &.commits-stat { |
120 | 116 | display: block; |
121 | - margin-top: 5px; | |
117 | + padding: 3px; | |
118 | + margin-top: 3px; | |
119 | + | |
120 | + &:hover { | |
121 | + background: none; | |
122 | + } | |
122 | 123 | } |
123 | 124 | } |
124 | 125 | } | ... | ... |
app/assets/stylesheets/sections/graph.scss
1 | -.graph_holder { | |
1 | +.graph_holder { | |
2 | 2 | border: 1px solid #aaa; |
3 | 3 | padding: 1px; |
4 | 4 | |
5 | 5 | |
6 | - h4 { | |
6 | + h4 { | |
7 | 7 | padding: 0 10px; |
8 | 8 | border-bottom: 1px solid #bbb; |
9 | 9 | @include bg-gray-gradient; |
10 | 10 | } |
11 | 11 | |
12 | - .graph { | |
12 | + .graph { | |
13 | 13 | background: #f1f1f1; |
14 | 14 | height: 500px; |
15 | 15 | overflow-y: scroll; |
... | ... | @@ -17,3 +17,16 @@ |
17 | 17 | } |
18 | 18 | } |
19 | 19 | |
20 | +.graphs { | |
21 | + .graph-author-commits-count { | |
22 | + } | |
23 | + | |
24 | + .graph-additions { | |
25 | + color: #4a2; | |
26 | + } | |
27 | + | |
28 | + .graph-deletions { | |
29 | + color: #d12f19; | |
30 | + } | |
31 | +} | |
32 | + | ... | ... |
app/assets/stylesheets/sections/header.scss
... | ... | @@ -120,7 +120,7 @@ header { |
120 | 120 | border-bottom: 1px solid #AAA; |
121 | 121 | |
122 | 122 | .nav > li > a { |
123 | - color: #DDD; | |
123 | + color: #AAA; | |
124 | 124 | text-shadow: 0 1px 0 #444; |
125 | 125 | |
126 | 126 | &:hover { |
... | ... | @@ -130,6 +130,10 @@ header { |
130 | 130 | } |
131 | 131 | } |
132 | 132 | |
133 | + .turbolink-spinner { | |
134 | + color: #FFF; | |
135 | + } | |
136 | + | |
133 | 137 | .search { |
134 | 138 | .search-input { |
135 | 139 | background-color: #D2D5DA; |
... | ... | @@ -156,7 +160,10 @@ header { |
156 | 160 | } |
157 | 161 | .project_name { |
158 | 162 | a { |
159 | - color: #FFF; | |
163 | + color: #DDD; | |
164 | + &:hover { | |
165 | + color: #FFF; | |
166 | + } | |
160 | 167 | } |
161 | 168 | color: #fff; |
162 | 169 | text-shadow: 0 1px 1px #444; | ... | ... |
app/assets/stylesheets/sections/login.scss
app/assets/stylesheets/sections/nav.scss
1 | 1 | .main-nav { |
2 | + background: #f5f5f5; | |
2 | 3 | margin: 30px 0; |
3 | - margin-top: 10px; | |
4 | + margin-top: 0; | |
5 | + padding-top: 4px; | |
4 | 6 | border-bottom: 1px solid #E1E1E1; |
5 | 7 | |
6 | 8 | ul { |
7 | 9 | margin: auto; |
8 | - height: 39px; | |
9 | - position: relative; | |
10 | - top: 3px; | |
10 | + height: 40px; | |
11 | 11 | overflow: hidden; |
12 | 12 | .count { |
13 | 13 | font-weight: normal; |
... | ... | @@ -33,10 +33,29 @@ |
33 | 33 | display: table-cell; |
34 | 34 | width: 1%; |
35 | 35 | &.active { |
36 | - border-bottom: 3px solid #777; | |
37 | 36 | a { |
38 | 37 | color: $style_color; |
39 | 38 | font-weight: bolder; |
39 | + | |
40 | + &:after { | |
41 | + content: ''; | |
42 | + display: block; | |
43 | + position: relative; | |
44 | + bottom: 8px; | |
45 | + left: 50%; | |
46 | + width: 0; | |
47 | + height: 0; | |
48 | + border-color: transparent transparent #777 transparent; | |
49 | + border-style: solid; | |
50 | + border-width: 6px; | |
51 | + margin-left: -6px; | |
52 | + } | |
53 | + } | |
54 | + } | |
55 | + | |
56 | + &:hover { | |
57 | + a { | |
58 | + color: $style_color; | |
40 | 59 | } |
41 | 60 | } |
42 | 61 | |
... | ... | @@ -54,11 +73,13 @@ |
54 | 73 | display: block; |
55 | 74 | text-align: center; |
56 | 75 | font-weight: normal; |
57 | - height: 36px; | |
76 | + height: 38px; | |
58 | 77 | line-height: 34px; |
59 | 78 | color: #777; |
60 | 79 | text-shadow: 0 1px 1px white; |
61 | 80 | padding: 0 10px; |
81 | + text-decoration: none; | |
82 | + padding-top: 2px; | |
62 | 83 | } |
63 | 84 | } |
64 | 85 | } | ... | ... |
app/assets/stylesheets/sections/themes.scss
app/assets/stylesheets/sections/tree.scss
app/assets/stylesheets/themes/ui_basic.scss
app/assets/stylesheets/themes/ui_color.scss
... | ... | @@ -16,15 +16,15 @@ |
16 | 16 | @extend .header-dark; |
17 | 17 | &.navbar-gitlab { |
18 | 18 | .navbar-inner { |
19 | - background: #657; | |
19 | + background: #547; | |
20 | 20 | .app_logo { |
21 | 21 | &:hover { |
22 | - background-color: #6A5A7A; | |
22 | + background-color: #435; | |
23 | 23 | } |
24 | 24 | } |
25 | 25 | .separator { |
26 | - background: #546; | |
27 | - border-left: 1px solid #706080; | |
26 | + background: #435; | |
27 | + border-left: 1px solid #658; | |
28 | 28 | } |
29 | 29 | } |
30 | 30 | } | ... | ... |
app/assets/stylesheets/themes/ui_gray.scss
... | ... | @@ -16,15 +16,15 @@ |
16 | 16 | @extend .header-dark; |
17 | 17 | &.navbar-gitlab { |
18 | 18 | .navbar-inner { |
19 | - background: #708090; | |
19 | + background: #373737; | |
20 | 20 | .app_logo { |
21 | 21 | &:hover { |
22 | - background-color: #6A7A8A; | |
22 | + background-color: #272727; | |
23 | 23 | } |
24 | 24 | } |
25 | 25 | .separator { |
26 | - background: #607080; | |
27 | - border-left: 1px solid #8090A0; | |
26 | + background: #272727; | |
27 | + border-left: 1px solid #474747; | |
28 | 28 | } |
29 | 29 | } |
30 | 30 | } | ... | ... |
app/assets/stylesheets/themes/ui_modern.scss
... | ... | @@ -16,15 +16,15 @@ |
16 | 16 | @extend .header-dark; |
17 | 17 | &.navbar-gitlab { |
18 | 18 | .navbar-inner { |
19 | - background: #567; | |
19 | + background: #345; | |
20 | 20 | .app_logo { |
21 | 21 | &:hover { |
22 | - background-color: #516171; | |
22 | + background-color: #234; | |
23 | 23 | } |
24 | 24 | } |
25 | 25 | .separator { |
26 | - background: #456; | |
27 | - border-left: 1px solid #678; | |
26 | + background: #234; | |
27 | + border-left: 1px solid #456; | |
28 | 28 | } |
29 | 29 | } |
30 | 30 | } | ... | ... |
app/contexts/projects/create_context.rb
... | ... | @@ -33,7 +33,7 @@ module Projects |
33 | 33 | # Find matching namespace and check if it allowed |
34 | 34 | # for current user if namespace_id passed. |
35 | 35 | if allowed_namespace?(current_user, namespace_id) |
36 | - @project.namespace_id = namespace_id unless namespace_id == Namespace.global_id | |
36 | + @project.namespace_id = namespace_id | |
37 | 37 | else |
38 | 38 | deny_namespace |
39 | 39 | return @project |
... | ... | @@ -48,6 +48,7 @@ module Projects |
48 | 48 | # Import project from cloneable resource |
49 | 49 | if @project.valid? && @project.import_url.present? |
50 | 50 | shell = Gitlab::Shell.new |
51 | + | |
51 | 52 | if shell.import_repository(@project.path_with_namespace, @project.import_url) |
52 | 53 | # We should create satellite for imported repo |
53 | 54 | @project.satellite.create unless @project.satellite.exists? |
... | ... | @@ -59,7 +60,11 @@ module Projects |
59 | 60 | end |
60 | 61 | |
61 | 62 | if @project.save |
62 | - @project.users_projects.create(project_access: UsersProject::MASTER, user: current_user) | |
63 | + unless @project.group | |
64 | + @project.users_projects.create(project_access: UsersProject::MASTER, user: current_user) | |
65 | + end | |
66 | + | |
67 | + @project.discover_default_branch | |
63 | 68 | end |
64 | 69 | |
65 | 70 | @project |
... | ... | @@ -75,12 +80,8 @@ module Projects |
75 | 80 | end |
76 | 81 | |
77 | 82 | def allowed_namespace?(user, namespace_id) |
78 | - if namespace_id == Namespace.global_id | |
79 | - return user.admin | |
80 | - else | |
81 | - namespace = Namespace.find_by_id(namespace_id) | |
82 | - current_user.can?(:manage_namespace, namespace) | |
83 | - end | |
83 | + namespace = Namespace.find_by_id(namespace_id) | |
84 | + current_user.can?(:manage_namespace, namespace) | |
84 | 85 | end |
85 | 86 | end |
86 | 87 | end | ... | ... |
app/contexts/projects/transfer_context.rb
... | ... | @@ -5,12 +5,7 @@ module Projects |
5 | 5 | allowed_transfer = can?(current_user, :change_namespace, project) || role == :admin |
6 | 6 | |
7 | 7 | if allowed_transfer && namespace_id.present? |
8 | - if namespace_id == Namespace.global_id | |
9 | - if project.namespace.present? | |
10 | - # Transfer to global namespace from anyone | |
11 | - project.transfer(nil) | |
12 | - end | |
13 | - elsif namespace_id.to_i != project.namespace_id | |
8 | + if namespace_id.to_i != project.namespace_id | |
14 | 9 | # Transfer to someone namespace |
15 | 10 | namespace = Namespace.find(namespace_id) |
16 | 11 | project.transfer(namespace) | ... | ... |
app/controllers/admin/groups_controller.rb
... | ... | @@ -25,7 +25,7 @@ class Admin::GroupsController < Admin::ApplicationController |
25 | 25 | if @group.save |
26 | 26 | redirect_to [:admin, @group], notice: 'Group was successfully created.' |
27 | 27 | else |
28 | - render action: "new" | |
28 | + render "new" | |
29 | 29 | end |
30 | 30 | end |
31 | 31 | |
... | ... | @@ -34,42 +34,23 @@ class Admin::GroupsController < Admin::ApplicationController |
34 | 34 | owner_id =group_params.delete(:owner_id) |
35 | 35 | |
36 | 36 | if owner_id |
37 | - @group.owner = User.find(owner_id) | |
37 | + @group.change_owner(User.find(owner_id)) | |
38 | 38 | end |
39 | 39 | |
40 | 40 | if @group.update_attributes(group_params) |
41 | 41 | redirect_to [:admin, @group], notice: 'Group was successfully updated.' |
42 | 42 | else |
43 | - render action: "edit" | |
43 | + render "edit" | |
44 | 44 | end |
45 | 45 | end |
46 | 46 | |
47 | - def project_update | |
48 | - project_ids = params[:project_ids] | |
49 | - | |
50 | - Project.where(id: project_ids).each do |project| | |
51 | - project.transfer(@group) | |
52 | - end | |
53 | - | |
54 | - redirect_to :back, notice: 'Group was successfully updated.' | |
55 | - end | |
56 | - | |
57 | - def remove_project | |
58 | - @project = Project.find(params[:project_id]) | |
59 | - @project.transfer(nil) | |
60 | - | |
61 | - redirect_to :back, notice: 'Group was successfully updated.' | |
62 | - end | |
63 | - | |
64 | 47 | def project_teams_update |
65 | - @group.add_users_to_project_teams(params[:user_ids].split(','), params[:project_access]) | |
48 | + @group.add_users(params[:user_ids].split(','), params[:group_access]) | |
66 | 49 | |
67 | 50 | redirect_to [:admin, @group], notice: 'Users were successfully added.' |
68 | 51 | end |
69 | 52 | |
70 | 53 | def destroy |
71 | - @group.truncate_teams | |
72 | - | |
73 | 54 | @group.destroy |
74 | 55 | |
75 | 56 | redirect_to admin_groups_path, notice: 'Group was successfully deleted.' | ... | ... |
... | ... | @@ -0,0 +1,9 @@ |
1 | +class Admin::MembersController < Admin::ApplicationController | |
2 | + def destroy | |
3 | + user = User.find_by_username(params[:id]) | |
4 | + project = Project.find_with_namespace(params[:project_id]) | |
5 | + project.users_projects.where(user_id: user).first.destroy | |
6 | + | |
7 | + redirect_to :back | |
8 | + end | |
9 | +end | ... | ... |
app/controllers/admin/projects/application_controller.rb
... | ... | @@ -1,11 +0,0 @@ |
1 | -# Provides a base class for Admin controllers to subclass | |
2 | -# | |
3 | -# Automatically sets the layout and ensures an administrator is logged in | |
4 | -class Admin::Projects::ApplicationController < Admin::ApplicationController | |
5 | - | |
6 | - protected | |
7 | - | |
8 | - def project | |
9 | - @project ||= Project.find_with_namespace(params[:project_id]) | |
10 | - end | |
11 | -end |
app/controllers/admin/projects/members_controller.rb
... | ... | @@ -1,32 +0,0 @@ |
1 | -class Admin::Projects::MembersController < Admin::Projects::ApplicationController | |
2 | - def edit | |
3 | - @member = team_member | |
4 | - @project = project | |
5 | - @team_member_relation = team_member_relation | |
6 | - end | |
7 | - | |
8 | - def update | |
9 | - if team_member_relation.update_attributes(params[:team_member]) | |
10 | - redirect_to [:admin, project], notice: 'Project Access was successfully updated.' | |
11 | - else | |
12 | - render action: "edit" | |
13 | - end | |
14 | - end | |
15 | - | |
16 | - def destroy | |
17 | - team_member_relation.destroy | |
18 | - | |
19 | - redirect_to :back | |
20 | - end | |
21 | - | |
22 | - private | |
23 | - | |
24 | - def team_member | |
25 | - @member ||= project.users.find_by_username(params[:id]) | |
26 | - end | |
27 | - | |
28 | - def team_member_relation | |
29 | - team_member.users_projects.find_by_project_id(project) | |
30 | - end | |
31 | - | |
32 | -end |
app/controllers/admin/projects_controller.rb
... | ... | @@ -9,13 +9,13 @@ class Admin::ProjectsController < Admin::ApplicationController |
9 | 9 | @projects = @projects.where(public: true) if params[:public_only].present? |
10 | 10 | @projects = @projects.with_push if params[:with_push].present? |
11 | 11 | @projects = @projects.abandoned if params[:abandoned].present? |
12 | - @projects = @projects.where(namespace_id: nil) if params[:namespace_id] == Namespace.global_id | |
13 | 12 | @projects = @projects.search(params[:name]) if params[:name].present? |
14 | 13 | @projects = @projects.includes(:namespace).order("namespaces.path, projects.name ASC").page(params[:page]).per(20) |
15 | 14 | end |
16 | 15 | |
17 | 16 | def show |
18 | 17 | @repository = @project.repository |
18 | + @group = @project.group | |
19 | 19 | end |
20 | 20 | |
21 | 21 | protected | ... | ... |
app/controllers/admin/teams/application_controller.rb
... | ... | @@ -1,11 +0,0 @@ |
1 | -# Provides a base class for Admin controllers to subclass | |
2 | -# | |
3 | -# Automatically sets the layout and ensures an administrator is logged in | |
4 | -class Admin::Teams::ApplicationController < Admin::ApplicationController | |
5 | - | |
6 | - private | |
7 | - | |
8 | - def user_team | |
9 | - @team = UserTeam.find_by_path(params[:team_id]) | |
10 | - end | |
11 | -end |
app/controllers/admin/teams/members_controller.rb
... | ... | @@ -1,40 +0,0 @@ |
1 | -class Admin::Teams::MembersController < Admin::Teams::ApplicationController | |
2 | - def new | |
3 | - @users = User.potential_team_members(user_team) | |
4 | - end | |
5 | - | |
6 | - def create | |
7 | - unless params[:user_ids].blank? | |
8 | - user_ids = params[:user_ids] | |
9 | - access = params[:default_project_access] | |
10 | - is_admin = params[:group_admin] | |
11 | - user_team.add_members(user_ids, access, is_admin) | |
12 | - end | |
13 | - | |
14 | - redirect_to admin_team_path(user_team), notice: 'Members were successfully added into Team of users.' | |
15 | - end | |
16 | - | |
17 | - def edit | |
18 | - team_member | |
19 | - end | |
20 | - | |
21 | - def update | |
22 | - options = {default_projects_access: params[:default_project_access], group_admin: params[:group_admin]} | |
23 | - if user_team.update_membership(team_member, options) | |
24 | - redirect_to admin_team_path(user_team), notice: "Membership for #{team_member.name} was successfully updated in Team of users." | |
25 | - else | |
26 | - render :edit | |
27 | - end | |
28 | - end | |
29 | - | |
30 | - def destroy | |
31 | - user_team.remove_member(team_member) | |
32 | - redirect_to admin_team_path(user_team), notice: "Member #{team_member.name} was successfully removed from Team of users." | |
33 | - end | |
34 | - | |
35 | - protected | |
36 | - | |
37 | - def team_member | |
38 | - @member ||= user_team.members.find_by_username(params[:id]) | |
39 | - end | |
40 | -end |
app/controllers/admin/teams/projects_controller.rb
... | ... | @@ -1,41 +0,0 @@ |
1 | -class Admin::Teams::ProjectsController < Admin::Teams::ApplicationController | |
2 | - def new | |
3 | - @projects = Project.scoped | |
4 | - @projects = @projects.without_team(user_team) if user_team.projects.any? | |
5 | - #@projects.reject!(&:empty_repo?) | |
6 | - end | |
7 | - | |
8 | - def create | |
9 | - unless params[:project_ids].blank? | |
10 | - project_ids = params[:project_ids] | |
11 | - access = params[:greatest_project_access] | |
12 | - user_team.assign_to_projects(project_ids, access) | |
13 | - end | |
14 | - | |
15 | - redirect_to admin_team_path(user_team), notice: 'Team of users was successfully assigned to projects.' | |
16 | - end | |
17 | - | |
18 | - def edit | |
19 | - team_project | |
20 | - end | |
21 | - | |
22 | - def update | |
23 | - if user_team.update_project_access(team_project, params[:greatest_project_access]) | |
24 | - redirect_to admin_team_path(user_team), notice: 'Access was successfully updated.' | |
25 | - else | |
26 | - render :edit | |
27 | - end | |
28 | - end | |
29 | - | |
30 | - def destroy | |
31 | - user_team.resign_from_project(team_project) | |
32 | - redirect_to admin_team_path(user_team), notice: 'Team of users was successfully reassigned from project.' | |
33 | - end | |
34 | - | |
35 | - protected | |
36 | - | |
37 | - def team_project | |
38 | - @project ||= user_team.projects.find_with_namespace(params[:id]) | |
39 | - end | |
40 | - | |
41 | -end |
app/controllers/admin/teams_controller.rb
... | ... | @@ -1,59 +0,0 @@ |
1 | -class Admin::TeamsController < Admin::ApplicationController | |
2 | - def index | |
3 | - @teams = UserTeam.order('name ASC') | |
4 | - @teams = @teams.search(params[:name]) if params[:name].present? | |
5 | - @teams = @teams.page(params[:page]).per(20) | |
6 | - end | |
7 | - | |
8 | - def show | |
9 | - user_team | |
10 | - end | |
11 | - | |
12 | - def new | |
13 | - @team = UserTeam.new | |
14 | - end | |
15 | - | |
16 | - def edit | |
17 | - user_team | |
18 | - end | |
19 | - | |
20 | - def create | |
21 | - @team = UserTeam.new(params[:user_team]) | |
22 | - @team.path = @team.name.dup.parameterize if @team.name | |
23 | - @team.owner = current_user | |
24 | - | |
25 | - if @team.save | |
26 | - redirect_to admin_team_path(@team), notice: 'Team of users was successfully created.' | |
27 | - else | |
28 | - render action: "new" | |
29 | - end | |
30 | - end | |
31 | - | |
32 | - def update | |
33 | - user_team_params = params[:user_team].dup | |
34 | - owner_id = user_team_params.delete(:owner_id) | |
35 | - | |
36 | - if owner_id | |
37 | - user_team.owner = User.find(owner_id) | |
38 | - end | |
39 | - | |
40 | - if user_team.update_attributes(user_team_params) | |
41 | - redirect_to admin_team_path(user_team), notice: 'Team of users was successfully updated.' | |
42 | - else | |
43 | - render action: "edit" | |
44 | - end | |
45 | - end | |
46 | - | |
47 | - def destroy | |
48 | - user_team.destroy | |
49 | - | |
50 | - redirect_to admin_teams_path, notice: 'Team of users was successfully deleted.' | |
51 | - end | |
52 | - | |
53 | - protected | |
54 | - | |
55 | - def user_team | |
56 | - @team ||= UserTeam.find_by_path(params[:id]) | |
57 | - end | |
58 | - | |
59 | -end |
app/controllers/admin/users_controller.rb
1 | 1 | class Admin::UsersController < Admin::ApplicationController |
2 | - before_filter :admin_user, only: [:show, :edit, :update, :destroy] | |
2 | + before_filter :user, only: [:show, :edit, :update, :destroy] | |
3 | 3 | |
4 | 4 | def index |
5 | - @admin_users = User.scoped | |
6 | - @admin_users = @admin_users.filter(params[:filter]) | |
7 | - @admin_users = @admin_users.search(params[:name]) if params[:name].present? | |
8 | - @admin_users = @admin_users.alphabetically.page(params[:page]) | |
5 | + @users = User.scoped | |
6 | + @users = @users.filter(params[:filter]) | |
7 | + @users = @users.search(params[:name]) if params[:name].present? | |
8 | + @users = @users.alphabetically.page(params[:page]) | |
9 | 9 | end |
10 | 10 | |
11 | 11 | def show |
12 | - # Projects user can be added to | |
13 | - @not_in_projects = Project.scoped | |
14 | - @not_in_projects = @not_in_projects.without_user(admin_user) if admin_user.authorized_projects.present? | |
15 | - | |
16 | - # Projects he already own or joined | |
17 | - @projects = admin_user.authorized_projects | |
12 | + @projects = user.authorized_projects | |
18 | 13 | end |
19 | 14 | |
20 | - def team_update | |
21 | - UsersProject.add_users_into_projects( | |
22 | - params[:project_ids], | |
23 | - [admin_user.id], | |
24 | - params[:project_access] | |
25 | - ) | |
26 | - | |
27 | - redirect_to [:admin, admin_user], notice: 'Teams were successfully updated.' | |
28 | - end | |
29 | - | |
30 | - | |
31 | 15 | def new |
32 | - @admin_user = User.new.with_defaults | |
16 | + @user = User.new.with_defaults | |
33 | 17 | end |
34 | 18 | |
35 | 19 | def edit |
36 | - admin_user | |
20 | + user | |
37 | 21 | end |
38 | 22 | |
39 | 23 | def block |
40 | - if admin_user.block | |
24 | + if user.block | |
41 | 25 | redirect_to :back, alert: "Successfully blocked" |
42 | 26 | else |
43 | 27 | redirect_to :back, alert: "Error occured. User was not blocked" |
... | ... | @@ -45,7 +29,7 @@ class Admin::UsersController < Admin::ApplicationController |
45 | 29 | end |
46 | 30 | |
47 | 31 | def unblock |
48 | - if admin_user.activate | |
32 | + if user.activate | |
49 | 33 | redirect_to :back, alert: "Successfully unblocked" |
50 | 34 | else |
51 | 35 | redirect_to :back, alert: "Error occured. User was not unblocked" |
... | ... | @@ -60,17 +44,17 @@ class Admin::UsersController < Admin::ApplicationController |
60 | 44 | password_expires_at: Time.now |
61 | 45 | } |
62 | 46 | |
63 | - @admin_user = User.new(params[:user].merge(opts), as: :admin) | |
64 | - @admin_user.admin = (admin && admin.to_i > 0) | |
65 | - @admin_user.created_by_id = current_user.id | |
47 | + @user = User.new(params[:user].merge(opts), as: :admin) | |
48 | + @user.admin = (admin && admin.to_i > 0) | |
49 | + @user.created_by_id = current_user.id | |
66 | 50 | |
67 | 51 | respond_to do |format| |
68 | - if @admin_user.save | |
69 | - format.html { redirect_to [:admin, @admin_user], notice: 'User was successfully created.' } | |
70 | - format.json { render json: @admin_user, status: :created, location: @admin_user } | |
52 | + if @user.save | |
53 | + format.html { redirect_to [:admin, @user], notice: 'User was successfully created.' } | |
54 | + format.json { render json: @user, status: :created, location: @user } | |
71 | 55 | else |
72 | - format.html { render action: "new" } | |
73 | - format.json { render json: @admin_user.errors, status: :unprocessable_entity } | |
56 | + format.html { render "new" } | |
57 | + format.json { render json: @user.errors, status: :unprocessable_entity } | |
74 | 58 | end |
75 | 59 | end |
76 | 60 | end |
... | ... | @@ -83,26 +67,26 @@ class Admin::UsersController < Admin::ApplicationController |
83 | 67 | params[:user].delete(:password_confirmation) |
84 | 68 | end |
85 | 69 | |
86 | - admin_user.admin = (admin && admin.to_i > 0) | |
70 | + user.admin = (admin && admin.to_i > 0) | |
87 | 71 | |
88 | 72 | respond_to do |format| |
89 | - if admin_user.update_attributes(params[:user], as: :admin) | |
90 | - format.html { redirect_to [:admin, admin_user], notice: 'User was successfully updated.' } | |
73 | + if user.update_attributes(params[:user], as: :admin) | |
74 | + format.html { redirect_to [:admin, user], notice: 'User was successfully updated.' } | |
91 | 75 | format.json { head :ok } |
92 | 76 | else |
93 | 77 | # restore username to keep form action url. |
94 | - admin_user.username = params[:id] | |
95 | - format.html { render action: "edit" } | |
96 | - format.json { render json: admin_user.errors, status: :unprocessable_entity } | |
78 | + user.username = params[:id] | |
79 | + format.html { render "edit" } | |
80 | + format.json { render json: user.errors, status: :unprocessable_entity } | |
97 | 81 | end |
98 | 82 | end |
99 | 83 | end |
100 | 84 | |
101 | 85 | def destroy |
102 | - if admin_user.personal_projects.count > 0 | |
86 | + if user.personal_projects.count > 0 | |
103 | 87 | redirect_to admin_users_path, alert: "User is a project owner and can't be removed." and return |
104 | 88 | end |
105 | - admin_user.destroy | |
89 | + user.destroy | |
106 | 90 | |
107 | 91 | respond_to do |format| |
108 | 92 | format.html { redirect_to admin_users_path } |
... | ... | @@ -112,7 +96,7 @@ class Admin::UsersController < Admin::ApplicationController |
112 | 96 | |
113 | 97 | protected |
114 | 98 | |
115 | - def admin_user | |
116 | - @admin_user ||= User.find_by_username!(params[:id]) | |
99 | + def user | |
100 | + @user ||= User.find_by_username!(params[:id]) | |
117 | 101 | end |
118 | 102 | end | ... | ... |
app/controllers/application_controller.rb
... | ... | @@ -95,14 +95,6 @@ class ApplicationController < ActionController::Base |
95 | 95 | return access_denied! unless can?(current_user, :create_team, nil) |
96 | 96 | end |
97 | 97 | |
98 | - def authorize_manage_user_team! | |
99 | - return access_denied! unless user_team.present? && can?(current_user, :manage_user_team, user_team) | |
100 | - end | |
101 | - | |
102 | - def authorize_admin_user_team! | |
103 | - return access_denied! unless user_team.present? && can?(current_user, :admin_user_team, user_team) | |
104 | - end | |
105 | - | |
106 | 98 | def access_denied! |
107 | 99 | render "errors/access_denied", layout: "errors", status: 404 |
108 | 100 | end | ... | ... |
app/controllers/blame_controller.rb
... | ... | @@ -1,14 +0,0 @@ |
1 | -# Controller for viewing a file's blame | |
2 | -class BlameController < ProjectResourceController | |
3 | - include ExtractsPath | |
4 | - | |
5 | - # Authorize | |
6 | - before_filter :authorize_read_project! | |
7 | - before_filter :authorize_code_access! | |
8 | - before_filter :require_non_empty_project | |
9 | - | |
10 | - def show | |
11 | - @blob = Gitlab::Git::Blob.new(@repository, @commit.id, @ref, @path) | |
12 | - @blame = Gitlab::Git::Blame.new(project.repository, @commit.id, @path) | |
13 | - end | |
14 | -end |
app/controllers/blob_controller.rb
... | ... | @@ -1,13 +0,0 @@ |
1 | -# Controller for viewing a file's blame | |
2 | -class BlobController < ProjectResourceController | |
3 | - include ExtractsPath | |
4 | - | |
5 | - # Authorize | |
6 | - before_filter :authorize_read_project! | |
7 | - before_filter :authorize_code_access! | |
8 | - before_filter :require_non_empty_project | |
9 | - | |
10 | - def show | |
11 | - @blob = Gitlab::Git::Blob.new(@repository, @commit.id, @ref, @path) | |
12 | - end | |
13 | -end |
app/controllers/commit_controller.rb
... | ... | @@ -1,43 +0,0 @@ |
1 | -# Controller for a specific Commit | |
2 | -# | |
3 | -# Not to be confused with CommitsController, plural. | |
4 | -class CommitController < ProjectResourceController | |
5 | - # Authorize | |
6 | - before_filter :authorize_read_project! | |
7 | - before_filter :authorize_code_access! | |
8 | - before_filter :require_non_empty_project | |
9 | - | |
10 | - def show | |
11 | - result = CommitLoadContext.new(project, current_user, params).execute | |
12 | - | |
13 | - @commit = result[:commit] | |
14 | - | |
15 | - if @commit.nil? | |
16 | - git_not_found! | |
17 | - return | |
18 | - end | |
19 | - | |
20 | - @suppress_diff = result[:suppress_diff] | |
21 | - | |
22 | - @note = result[:note] | |
23 | - @line_notes = result[:line_notes] | |
24 | - @notes_count = result[:notes_count] | |
25 | - @target_type = :commit | |
26 | - @target_id = @commit.id | |
27 | - | |
28 | - @comments_allowed = @reply_allowed = true | |
29 | - @comments_target = { noteable_type: 'Commit', | |
30 | - commit_id: @commit.id } | |
31 | - | |
32 | - respond_to do |format| | |
33 | - format.html do | |
34 | - if result[:status] == :huge_commit | |
35 | - render "huge_commit" and return | |
36 | - end | |
37 | - end | |
38 | - | |
39 | - format.diff { render text: @commit.to_diff } | |
40 | - format.patch { render text: @commit.to_patch } | |
41 | - end | |
42 | - end | |
43 | -end |
app/controllers/commits_controller.rb
... | ... | @@ -1,23 +0,0 @@ |
1 | -require "base64" | |
2 | - | |
3 | -class CommitsController < ProjectResourceController | |
4 | - include ExtractsPath | |
5 | - | |
6 | - # Authorize | |
7 | - before_filter :authorize_read_project! | |
8 | - before_filter :authorize_code_access! | |
9 | - before_filter :require_non_empty_project | |
10 | - | |
11 | - def show | |
12 | - @repo = @project.repository | |
13 | - @limit, @offset = (params[:limit] || 40), (params[:offset] || 0) | |
14 | - | |
15 | - @commits = @repo.commits(@ref, @path, @limit, @offset) | |
16 | - | |
17 | - respond_to do |format| | |
18 | - format.html # index.html.erb | |
19 | - format.js | |
20 | - format.atom { render layout: false } | |
21 | - end | |
22 | - end | |
23 | -end |
app/controllers/compare_controller.rb
... | ... | @@ -1,23 +0,0 @@ |
1 | -class CompareController < ProjectResourceController | |
2 | - # Authorize | |
3 | - before_filter :authorize_read_project! | |
4 | - before_filter :authorize_code_access! | |
5 | - before_filter :require_non_empty_project | |
6 | - | |
7 | - def index | |
8 | - end | |
9 | - | |
10 | - def show | |
11 | - compare = Gitlab::Git::Compare.new(project.repository, params[:from], params[:to]) | |
12 | - | |
13 | - @commits = compare.commits | |
14 | - @commit = compare.commit | |
15 | - @diffs = compare.diffs | |
16 | - @refs_are_same = compare.same | |
17 | - @line_notes = [] | |
18 | - end | |
19 | - | |
20 | - def create | |
21 | - redirect_to project_compare_path(@project, params[:from], params[:to]) | |
22 | - end | |
23 | -end |
app/controllers/dashboard_controller.rb
1 | 1 | class DashboardController < ApplicationController |
2 | 2 | respond_to :html |
3 | 3 | |
4 | - before_filter :load_projects | |
4 | + before_filter :load_projects, except: [:projects] | |
5 | 5 | before_filter :event_filter, only: :show |
6 | 6 | |
7 | 7 | def show |
8 | 8 | @groups = current_user.authorized_groups.sort_by(&:human_name) |
9 | 9 | @has_authorized_projects = @projects.count > 0 |
10 | - @teams = current_user.authorized_teams | |
11 | 10 | @projects_count = @projects.count |
12 | 11 | @projects = @projects.limit(20) |
13 | 12 | |
... | ... | @@ -27,18 +26,21 @@ class DashboardController < ApplicationController |
27 | 26 | def projects |
28 | 27 | @projects = case params[:scope] |
29 | 28 | when 'personal' then |
30 | - @projects.personal(current_user) | |
29 | + current_user.namespace.projects | |
31 | 30 | when 'joined' then |
32 | - @projects.joined(current_user) | |
31 | + current_user.authorized_projects.joined(current_user) | |
32 | + when 'owned' then | |
33 | + current_user.owned_projects | |
33 | 34 | else |
34 | - @projects | |
35 | - end | |
35 | + current_user.authorized_projects | |
36 | + end.sorted_by_activity | |
36 | 37 | |
37 | - @projects = @projects.tagged_with(params[:label]) if params[:label].present? | |
38 | 38 | @projects = @projects.search(params[:search]) if params[:search].present? |
39 | - @projects = @projects.page(params[:page]).per(30) | |
40 | 39 | |
41 | - @labels = Project.where(id: @projects.map(&:id)).tags_on(:labels) | |
40 | + @labels = current_user.authorized_projects.tags_on(:labels) | |
41 | + | |
42 | + @projects = @projects.tagged_with(params[:label]) if params[:label].present? | |
43 | + @projects = @projects.page(params[:page]).per(30) | |
42 | 44 | end |
43 | 45 | |
44 | 46 | # Get authored or assigned open merge requests | ... | ... |
app/controllers/deploy_keys_controller.rb
... | ... | @@ -1,59 +0,0 @@ |
1 | -class DeployKeysController < ProjectResourceController | |
2 | - respond_to :html | |
3 | - | |
4 | - # Authorize | |
5 | - before_filter :authorize_admin_project! | |
6 | - | |
7 | - def index | |
8 | - @enabled_keys = @project.deploy_keys.all | |
9 | - @available_keys = available_keys - @enabled_keys | |
10 | - end | |
11 | - | |
12 | - def show | |
13 | - @key = @project.deploy_keys.find(params[:id]) | |
14 | - end | |
15 | - | |
16 | - def new | |
17 | - @key = @project.deploy_keys.new | |
18 | - | |
19 | - respond_with(@key) | |
20 | - end | |
21 | - | |
22 | - def create | |
23 | - @key = DeployKey.new(params[:deploy_key]) | |
24 | - | |
25 | - if @key.valid? && @project.deploy_keys << @key | |
26 | - redirect_to project_deploy_keys_path(@project) | |
27 | - else | |
28 | - render "new" | |
29 | - end | |
30 | - end | |
31 | - | |
32 | - def destroy | |
33 | - @key = @project.deploy_keys.find(params[:id]) | |
34 | - @key.destroy | |
35 | - | |
36 | - respond_to do |format| | |
37 | - format.html { redirect_to project_deploy_keys_url } | |
38 | - format.js { render nothing: true } | |
39 | - end | |
40 | - end | |
41 | - | |
42 | - def enable | |
43 | - project.deploy_keys << available_keys.find(params[:id]) | |
44 | - | |
45 | - redirect_to project_deploy_keys_path(@project) | |
46 | - end | |
47 | - | |
48 | - def disable | |
49 | - @project.deploy_keys_projects.where(deploy_key_id: params[:id]).last.destroy | |
50 | - | |
51 | - redirect_to project_deploy_keys_path(@project) | |
52 | - end | |
53 | - | |
54 | - protected | |
55 | - | |
56 | - def available_keys | |
57 | - @available_keys ||= current_user.accessible_deploy_keys | |
58 | - end | |
59 | -end |
app/controllers/edit_tree_controller.rb
... | ... | @@ -1,49 +0,0 @@ |
1 | -# Controller for edit a repository's file | |
2 | -class EditTreeController < ProjectResourceController | |
3 | - include ExtractsPath | |
4 | - | |
5 | - # Authorize | |
6 | - before_filter :authorize_read_project! | |
7 | - before_filter :authorize_code_access! | |
8 | - before_filter :require_non_empty_project | |
9 | - | |
10 | - before_filter :edit_requirements, only: [:show, :update] | |
11 | - | |
12 | - def show | |
13 | - @last_commit = @project.repository.last_commit_for(@ref, @path).sha | |
14 | - end | |
15 | - | |
16 | - def update | |
17 | - edit_file_action = Gitlab::Satellite::EditFileAction.new(current_user, @project, @ref, @path) | |
18 | - updated_successfully = edit_file_action.commit!( | |
19 | - params[:content], | |
20 | - params[:commit_message], | |
21 | - params[:last_commit] | |
22 | - ) | |
23 | - | |
24 | - if updated_successfully | |
25 | - redirect_to project_blob_path(@project, @id), notice: "Your changes have been successfully commited" | |
26 | - else | |
27 | - flash[:notice] = "Your changes could not be commited, because the file has been changed" | |
28 | - render :show | |
29 | - end | |
30 | - end | |
31 | - | |
32 | - private | |
33 | - | |
34 | - def edit_requirements | |
35 | - @blob = Gitlab::Git::Blob.new(@repository, @commit.id, @ref, @path) | |
36 | - | |
37 | - unless @blob.exists? && @blob.text? | |
38 | - redirect_to project_blob_path(@project, @id), notice: "You can only edit text files" | |
39 | - end | |
40 | - | |
41 | - allowed = if project.protected_branch? @ref | |
42 | - can?(current_user, :push_code_to_protected_branches, project) | |
43 | - else | |
44 | - can?(current_user, :push_code, project) | |
45 | - end | |
46 | - | |
47 | - return access_denied! unless allowed | |
48 | - end | |
49 | -end |
app/controllers/graphs_controller.rb
... | ... | @@ -1,17 +0,0 @@ |
1 | -class GraphsController < ProjectResourceController | |
2 | - # Authorize | |
3 | - before_filter :authorize_read_project! | |
4 | - before_filter :authorize_code_access! | |
5 | - before_filter :require_non_empty_project | |
6 | - | |
7 | - def show | |
8 | - respond_to do |format| | |
9 | - format.html | |
10 | - format.js do | |
11 | - @repo = @project.repository | |
12 | - @stats = Gitlab::Git::GitStats.new(@repo.raw, @repo.root_ref) | |
13 | - @log = @stats.parsed_log.to_json | |
14 | - end | |
15 | - end | |
16 | - end | |
17 | -end |
app/controllers/groups_controller.rb
... | ... | @@ -63,19 +63,8 @@ class GroupsController < ApplicationController |
63 | 63 | |
64 | 64 | def people |
65 | 65 | @project = group.projects.find(params[:project_id]) if params[:project_id] |
66 | - @users = @project ? @project.users : group.users | |
67 | - @users.sort_by!(&:name) | |
68 | - | |
69 | - if @project | |
70 | - @team_member = @project.users_projects.new | |
71 | - else | |
72 | - @team_member = UsersProject.new | |
73 | - end | |
74 | - end | |
75 | - | |
76 | - def team_members | |
77 | - @group.add_users_to_project_teams(params[:user_ids].split(','), params[:project_access]) | |
78 | - redirect_to people_group_path(@group), notice: 'Users were successfully added.' | |
66 | + @members = group.users_groups.order('group_access DESC') | |
67 | + @users_group = UsersGroup.new | |
79 | 68 | end |
80 | 69 | |
81 | 70 | def edit |
... | ... | @@ -83,7 +72,7 @@ class GroupsController < ApplicationController |
83 | 72 | |
84 | 73 | def update |
85 | 74 | group_params = params[:group].dup |
86 | - owner_id =group_params.delete(:owner_id) | |
75 | + owner_id = group_params.delete(:owner_id) | |
87 | 76 | |
88 | 77 | if owner_id |
89 | 78 | @group.owner = User.find(owner_id) | ... | ... |
app/controllers/help_controller.rb
app/controllers/hooks_controller.rb
... | ... | @@ -1,37 +0,0 @@ |
1 | -class HooksController < ProjectResourceController | |
2 | - # Authorize | |
3 | - before_filter :authorize_read_project! | |
4 | - before_filter :authorize_admin_project!, only: [:new, :create, :destroy] | |
5 | - | |
6 | - respond_to :html | |
7 | - | |
8 | - def index | |
9 | - @hooks = @project.hooks.all | |
10 | - @hook = ProjectHook.new | |
11 | - end | |
12 | - | |
13 | - def create | |
14 | - @hook = @project.hooks.new(params[:hook]) | |
15 | - @hook.save | |
16 | - | |
17 | - if @hook.valid? | |
18 | - redirect_to project_hooks_path(@project) | |
19 | - else | |
20 | - @hooks = @project.hooks.all | |
21 | - render :index | |
22 | - end | |
23 | - end | |
24 | - | |
25 | - def test | |
26 | - TestHookContext.new(project, current_user, params).execute | |
27 | - | |
28 | - redirect_to :back | |
29 | - end | |
30 | - | |
31 | - def destroy | |
32 | - @hook = @project.hooks.find(params[:id]) | |
33 | - @hook.destroy | |
34 | - | |
35 | - redirect_to project_hooks_path(@project) | |
36 | - end | |
37 | -end |
app/controllers/issues_controller.rb
... | ... | @@ -1,114 +0,0 @@ |
1 | -class IssuesController < ProjectResourceController | |
2 | - before_filter :module_enabled | |
3 | - before_filter :issue, only: [:edit, :update, :show] | |
4 | - | |
5 | - # Allow read any issue | |
6 | - before_filter :authorize_read_issue! | |
7 | - | |
8 | - # Allow write(create) issue | |
9 | - before_filter :authorize_write_issue!, only: [:new, :create] | |
10 | - | |
11 | - # Allow modify issue | |
12 | - before_filter :authorize_modify_issue!, only: [:edit, :update] | |
13 | - | |
14 | - respond_to :js, :html | |
15 | - | |
16 | - def index | |
17 | - terms = params['issue_search'] | |
18 | - | |
19 | - @issues = issues_filtered | |
20 | - @issues = @issues.where("title LIKE ?", "%#{terms}%") if terms.present? | |
21 | - @issues = @issues.page(params[:page]).per(20) | |
22 | - | |
23 | - | |
24 | - assignee_id, milestone_id = params[:assignee_id], params[:milestone_id] | |
25 | - | |
26 | - @assignee = @project.users.find(assignee_id) if assignee_id.present? && !assignee_id.to_i.zero? | |
27 | - @milestone = @project.milestones.find(milestone_id) if milestone_id.present? && !milestone_id.to_i.zero? | |
28 | - | |
29 | - respond_to do |format| | |
30 | - format.html # index.html.erb | |
31 | - format.js | |
32 | - format.atom { render layout: false } | |
33 | - end | |
34 | - end | |
35 | - | |
36 | - def new | |
37 | - @issue = @project.issues.new(params[:issue]) | |
38 | - respond_with(@issue) | |
39 | - end | |
40 | - | |
41 | - def edit | |
42 | - respond_with(@issue) | |
43 | - end | |
44 | - | |
45 | - def show | |
46 | - @note = @project.notes.new(noteable: @issue) | |
47 | - @target_type = :issue | |
48 | - @target_id = @issue.id | |
49 | - | |
50 | - respond_to do |format| | |
51 | - format.html | |
52 | - format.js | |
53 | - end | |
54 | - end | |
55 | - | |
56 | - def create | |
57 | - @issue = @project.issues.new(params[:issue]) | |
58 | - @issue.author = current_user | |
59 | - @issue.save | |
60 | - | |
61 | - respond_to do |format| | |
62 | - format.html do | |
63 | - if @issue.valid? | |
64 | - redirect_to project_issue_path(@project, @issue) | |
65 | - else | |
66 | - render :new | |
67 | - end | |
68 | - end | |
69 | - format.js | |
70 | - end | |
71 | - end | |
72 | - | |
73 | - def update | |
74 | - @issue.update_attributes(params[:issue].merge(author_id_of_changes: current_user.id)) | |
75 | - | |
76 | - respond_to do |format| | |
77 | - format.js | |
78 | - format.html do | |
79 | - if @issue.valid? | |
80 | - redirect_to [@project, @issue] | |
81 | - else | |
82 | - render :edit | |
83 | - end | |
84 | - end | |
85 | - end | |
86 | - end | |
87 | - | |
88 | - def bulk_update | |
89 | - result = Issues::BulkUpdateContext.new(project, current_user, params).execute | |
90 | - redirect_to :back, notice: "#{result[:count]} issues updated" | |
91 | - end | |
92 | - | |
93 | - protected | |
94 | - | |
95 | - def issue | |
96 | - @issue ||= @project.issues.find(params[:id]) | |
97 | - end | |
98 | - | |
99 | - def authorize_modify_issue! | |
100 | - return render_404 unless can?(current_user, :modify_issue, @issue) | |
101 | - end | |
102 | - | |
103 | - def authorize_admin_issue! | |
104 | - return render_404 unless can?(current_user, :admin_issue, @issue) | |
105 | - end | |
106 | - | |
107 | - def module_enabled | |
108 | - return render_404 unless @project.issues_enabled | |
109 | - end | |
110 | - | |
111 | - def issues_filtered | |
112 | - @issues = Issues::ListContext.new(project, current_user, params).execute | |
113 | - end | |
114 | -end |
app/controllers/keys_controller.rb
... | ... | @@ -1,35 +0,0 @@ |
1 | -class KeysController < ApplicationController | |
2 | - layout "profile" | |
3 | - respond_to :js, :html | |
4 | - | |
5 | - def index | |
6 | - @keys = current_user.keys.all | |
7 | - end | |
8 | - | |
9 | - def show | |
10 | - @key = current_user.keys.find(params[:id]) | |
11 | - end | |
12 | - | |
13 | - def new | |
14 | - @key = current_user.keys.new | |
15 | - | |
16 | - respond_with(@key) | |
17 | - end | |
18 | - | |
19 | - def create | |
20 | - @key = current_user.keys.new(params[:key]) | |
21 | - @key.save | |
22 | - | |
23 | - respond_with(@key) | |
24 | - end | |
25 | - | |
26 | - def destroy | |
27 | - @key = current_user.keys.find(params[:id]) | |
28 | - @key.destroy | |
29 | - | |
30 | - respond_to do |format| | |
31 | - format.html { redirect_to keys_url } | |
32 | - format.js { render nothing: true } | |
33 | - end | |
34 | - end | |
35 | -end |
app/controllers/labels_controller.rb
... | ... | @@ -1,24 +0,0 @@ |
1 | -class LabelsController < ProjectResourceController | |
2 | - before_filter :module_enabled | |
3 | - | |
4 | - # Allow read any issue | |
5 | - before_filter :authorize_read_issue! | |
6 | - | |
7 | - respond_to :js, :html | |
8 | - | |
9 | - def index | |
10 | - @labels = @project.issues_labels | |
11 | - end | |
12 | - | |
13 | - def generate | |
14 | - Gitlab::IssuesLabels.generate(@project) | |
15 | - | |
16 | - redirect_to project_labels_path(@project) | |
17 | - end | |
18 | - | |
19 | - protected | |
20 | - | |
21 | - def module_enabled | |
22 | - return render_404 unless @project.issues_enabled | |
23 | - end | |
24 | -end |
app/controllers/merge_requests_controller.rb
... | ... | @@ -1,163 +0,0 @@ |
1 | -require 'gitlab/satellite/satellite' | |
2 | - | |
3 | -class MergeRequestsController < ProjectResourceController | |
4 | - before_filter :module_enabled | |
5 | - before_filter :merge_request, only: [:edit, :update, :show, :commits, :diffs, :automerge, :automerge_check, :ci_status] | |
6 | - before_filter :validates_merge_request, only: [:show, :diffs] | |
7 | - before_filter :define_show_vars, only: [:show, :diffs] | |
8 | - | |
9 | - # Allow read any merge_request | |
10 | - before_filter :authorize_read_merge_request! | |
11 | - | |
12 | - # Allow write(create) merge_request | |
13 | - before_filter :authorize_write_merge_request!, only: [:new, :create] | |
14 | - | |
15 | - # Allow modify merge_request | |
16 | - before_filter :authorize_modify_merge_request!, only: [:close, :edit, :update, :sort] | |
17 | - | |
18 | - def index | |
19 | - @merge_requests = MergeRequestsLoadContext.new(project, current_user, params).execute | |
20 | - end | |
21 | - | |
22 | - def show | |
23 | - respond_to do |format| | |
24 | - format.html | |
25 | - format.js | |
26 | - | |
27 | - format.diff { render text: @merge_request.to_diff } | |
28 | - format.patch { render text: @merge_request.to_patch } | |
29 | - end | |
30 | - end | |
31 | - | |
32 | - def diffs | |
33 | - @diffs = @merge_request.diffs | |
34 | - @commit = @merge_request.last_commit | |
35 | - | |
36 | - @comments_allowed = @reply_allowed = true | |
37 | - @comments_target = { noteable_type: 'MergeRequest', | |
38 | - noteable_id: @merge_request.id } | |
39 | - @line_notes = @merge_request.notes.where("line_code is not null") | |
40 | - end | |
41 | - | |
42 | - def new | |
43 | - @merge_request = @project.merge_requests.new(params[:merge_request]) | |
44 | - end | |
45 | - | |
46 | - def edit | |
47 | - end | |
48 | - | |
49 | - def create | |
50 | - @merge_request = @project.merge_requests.new(params[:merge_request]) | |
51 | - @merge_request.author = current_user | |
52 | - | |
53 | - if @merge_request.save | |
54 | - @merge_request.reload_code | |
55 | - redirect_to [@project, @merge_request], notice: 'Merge request was successfully created.' | |
56 | - else | |
57 | - render action: "new" | |
58 | - end | |
59 | - end | |
60 | - | |
61 | - def update | |
62 | - if @merge_request.update_attributes(params[:merge_request].merge(author_id_of_changes: current_user.id)) | |
63 | - @merge_request.reload_code | |
64 | - @merge_request.mark_as_unchecked | |
65 | - redirect_to [@project, @merge_request], notice: 'Merge request was successfully updated.' | |
66 | - else | |
67 | - render action: "edit" | |
68 | - end | |
69 | - end | |
70 | - | |
71 | - def automerge_check | |
72 | - if @merge_request.unchecked? | |
73 | - @merge_request.check_if_can_be_merged | |
74 | - end | |
75 | - render json: {merge_status: @merge_request.merge_status_name} | |
76 | - rescue Gitlab::SatelliteNotExistError | |
77 | - render json: {merge_status: :no_satellite} | |
78 | - end | |
79 | - | |
80 | - def automerge | |
81 | - return access_denied! unless allowed_to_merge? | |
82 | - | |
83 | - if @merge_request.opened? && @merge_request.can_be_merged? | |
84 | - @merge_request.should_remove_source_branch = params[:should_remove_source_branch] | |
85 | - @merge_request.automerge!(current_user) | |
86 | - @status = true | |
87 | - else | |
88 | - @status = false | |
89 | - end | |
90 | - end | |
91 | - | |
92 | - def branch_from | |
93 | - @commit = @repository.commit(params[:ref]) | |
94 | - end | |
95 | - | |
96 | - def branch_to | |
97 | - @commit = @repository.commit(params[:ref]) | |
98 | - end | |
99 | - | |
100 | - def ci_status | |
101 | - status = project.gitlab_ci_service.commit_status(merge_request.last_commit.sha) | |
102 | - response = { status: status } | |
103 | - | |
104 | - render json: response | |
105 | - end | |
106 | - | |
107 | - protected | |
108 | - | |
109 | - def merge_request | |
110 | - @merge_request ||= @project.merge_requests.find(params[:id]) | |
111 | - end | |
112 | - | |
113 | - def authorize_modify_merge_request! | |
114 | - return render_404 unless can?(current_user, :modify_merge_request, @merge_request) | |
115 | - end | |
116 | - | |
117 | - def authorize_admin_merge_request! | |
118 | - return render_404 unless can?(current_user, :admin_merge_request, @merge_request) | |
119 | - end | |
120 | - | |
121 | - def module_enabled | |
122 | - return render_404 unless @project.merge_requests_enabled | |
123 | - end | |
124 | - | |
125 | - def validates_merge_request | |
126 | - # Show git not found page if target branch doesn't exist | |
127 | - return invalid_mr unless @project.repository.branch_names.include?(@merge_request.target_branch) | |
128 | - | |
129 | - # Show git not found page if source branch doesn't exist | |
130 | - # and there is no saved commits between source & target branch | |
131 | - return invalid_mr if !@project.repository.branch_names.include?(@merge_request.source_branch) && @merge_request.commits.blank? | |
132 | - end | |
133 | - | |
134 | - def define_show_vars | |
135 | - # Build a note object for comment form | |
136 | - @note = @project.notes.new(noteable: @merge_request) | |
137 | - | |
138 | - # Get commits from repository | |
139 | - # or from cache if already merged | |
140 | - @commits = @merge_request.commits | |
141 | - | |
142 | - @allowed_to_merge = allowed_to_merge? | |
143 | - @show_merge_controls = @merge_request.opened? && @commits.any? && @allowed_to_merge | |
144 | - | |
145 | - @target_type = :merge_request | |
146 | - @target_id = @merge_request.id | |
147 | - end | |
148 | - | |
149 | - def allowed_to_merge? | |
150 | - action = if project.protected_branch?(@merge_request.target_branch) | |
151 | - :push_code_to_protected_branches | |
152 | - else | |
153 | - :push_code | |
154 | - end | |
155 | - | |
156 | - can?(current_user, action, @project) | |
157 | - end | |
158 | - | |
159 | - def invalid_mr | |
160 | - # Render special view for MR with removed source or target branch | |
161 | - render 'invalid' | |
162 | - end | |
163 | -end |
app/controllers/milestones_controller.rb
... | ... | @@ -1,94 +0,0 @@ |
1 | -class MilestonesController < ProjectResourceController | |
2 | - before_filter :module_enabled | |
3 | - before_filter :milestone, only: [:edit, :update, :destroy, :show] | |
4 | - | |
5 | - # Allow read any milestone | |
6 | - before_filter :authorize_read_milestone! | |
7 | - | |
8 | - # Allow admin milestone | |
9 | - before_filter :authorize_admin_milestone!, except: [:index, :show] | |
10 | - | |
11 | - respond_to :html | |
12 | - | |
13 | - def index | |
14 | - @milestones = case params[:f] | |
15 | - when 'all'; @project.milestones.order("state, due_date DESC") | |
16 | - when 'closed'; @project.milestones.closed.order("due_date DESC") | |
17 | - else @project.milestones.active.order("due_date DESC") | |
18 | - end | |
19 | - | |
20 | - @milestones = @milestones.includes(:project) | |
21 | - @milestones = @milestones.page(params[:page]).per(20) | |
22 | - end | |
23 | - | |
24 | - def new | |
25 | - @milestone = @project.milestones.new | |
26 | - respond_with(@milestone) | |
27 | - end | |
28 | - | |
29 | - def edit | |
30 | - respond_with(@milestone) | |
31 | - end | |
32 | - | |
33 | - def show | |
34 | - @issues = @milestone.issues | |
35 | - @users = @milestone.participants.uniq | |
36 | - @merge_requests = @milestone.merge_requests | |
37 | - | |
38 | - respond_to do |format| | |
39 | - format.html | |
40 | - format.js | |
41 | - end | |
42 | - end | |
43 | - | |
44 | - def create | |
45 | - @milestone = @project.milestones.new(params[:milestone]) | |
46 | - @milestone.author_id_of_changes = current_user.id | |
47 | - | |
48 | - if @milestone.save | |
49 | - redirect_to project_milestone_path(@project, @milestone) | |
50 | - else | |
51 | - render "new" | |
52 | - end | |
53 | - end | |
54 | - | |
55 | - def update | |
56 | - @milestone.update_attributes(params[:milestone].merge(author_id_of_changes: current_user.id)) | |
57 | - | |
58 | - respond_to do |format| | |
59 | - format.js | |
60 | - format.html do | |
61 | - if @milestone.valid? | |
62 | - redirect_to [@project, @milestone] | |
63 | - else | |
64 | - render :edit | |
65 | - end | |
66 | - end | |
67 | - end | |
68 | - end | |
69 | - | |
70 | - def destroy | |
71 | - return access_denied! unless can?(current_user, :admin_milestone, @milestone) | |
72 | - | |
73 | - @milestone.destroy | |
74 | - | |
75 | - respond_to do |format| | |
76 | - format.html { redirect_to project_milestones_path } | |
77 | - format.js { render nothing: true } | |
78 | - end | |
79 | - end | |
80 | - | |
81 | - protected | |
82 | - | |
83 | - def milestone | |
84 | - @milestone ||= @project.milestones.find(params[:id]) | |
85 | - end | |
86 | - | |
87 | - def authorize_admin_milestone! | |
88 | - return render_404 unless can?(current_user, :admin_milestone, @project) | |
89 | - end | |
90 | - | |
91 | - def module_enabled | |
92 | - return render_404 unless @project.issues_enabled | |
93 | - end | |
94 | -end |
app/controllers/network_controller.rb
... | ... | @@ -1,23 +0,0 @@ |
1 | -class NetworkController < ProjectResourceController | |
2 | - include ExtractsPath | |
3 | - include ApplicationHelper | |
4 | - | |
5 | - # Authorize | |
6 | - before_filter :authorize_read_project! | |
7 | - before_filter :authorize_code_access! | |
8 | - before_filter :require_non_empty_project | |
9 | - | |
10 | - def show | |
11 | - if @options[:q] | |
12 | - @commit = @project.repository.commit(@options[:q]) || @commit | |
13 | - end | |
14 | - | |
15 | - respond_to do |format| | |
16 | - format.html | |
17 | - | |
18 | - format.json do | |
19 | - @graph = Network::Graph.new(project, @ref, @commit, @options[:filter_ref]) | |
20 | - end | |
21 | - end | |
22 | - end | |
23 | -end |
app/controllers/notes_controller.rb
... | ... | @@ -1,102 +0,0 @@ |
1 | -class NotesController < ProjectResourceController | |
2 | - # Authorize | |
3 | - before_filter :authorize_read_note! | |
4 | - before_filter :authorize_write_note!, only: [:create] | |
5 | - | |
6 | - respond_to :js | |
7 | - | |
8 | - def index | |
9 | - @notes = Notes::LoadContext.new(project, current_user, params).execute | |
10 | - @target_type = params[:target_type].camelize | |
11 | - @target_id = params[:target_id] | |
12 | - | |
13 | - if params[:target_type] == "merge_request" | |
14 | - @discussions = discussions_from_notes | |
15 | - end | |
16 | - | |
17 | - respond_with(@notes) | |
18 | - end | |
19 | - | |
20 | - def create | |
21 | - @note = Notes::CreateContext.new(project, current_user, params).execute | |
22 | - @target_type = params[:target_type].camelize | |
23 | - @target_id = params[:target_id] | |
24 | - | |
25 | - respond_to do |format| | |
26 | - format.html {redirect_to :back} | |
27 | - format.js | |
28 | - end | |
29 | - end | |
30 | - | |
31 | - def destroy | |
32 | - @note = @project.notes.find(params[:id]) | |
33 | - return access_denied! unless can?(current_user, :admin_note, @note) | |
34 | - @note.destroy | |
35 | - | |
36 | - respond_to do |format| | |
37 | - format.js { render nothing: true } | |
38 | - end | |
39 | - end | |
40 | - | |
41 | - def update | |
42 | - @note = @project.notes.find(params[:id]) | |
43 | - return access_denied! unless can?(current_user, :admin_note, @note) | |
44 | - | |
45 | - @note.update_attributes(params[:note]) | |
46 | - | |
47 | - respond_to do |format| | |
48 | - format.js do | |
49 | - render js: { success: @note.valid?, id: @note.id, note: view_context.markdown(@note.note) }.to_json | |
50 | - end | |
51 | - format.html do | |
52 | - redirect_to :back | |
53 | - end | |
54 | - end | |
55 | - end | |
56 | - | |
57 | - def delete_attachment | |
58 | - @note = @project.notes.find(params[:id]) | |
59 | - @note.remove_attachment! | |
60 | - @note.update_attribute(:attachment, nil) | |
61 | - | |
62 | - respond_to do |format| | |
63 | - format.js { render nothing: true } | |
64 | - end | |
65 | - end | |
66 | - | |
67 | - def preview | |
68 | - render text: view_context.markdown(params[:note]) | |
69 | - end | |
70 | - | |
71 | - protected | |
72 | - | |
73 | - def discussion_notes_for(note) | |
74 | - @notes.select do |other_note| | |
75 | - note.discussion_id == other_note.discussion_id | |
76 | - end | |
77 | - end | |
78 | - | |
79 | - def discussions_from_notes | |
80 | - discussion_ids = [] | |
81 | - discussions = [] | |
82 | - | |
83 | - @notes.each do |note| | |
84 | - next if discussion_ids.include?(note.discussion_id) | |
85 | - | |
86 | - # don't group notes for the main target | |
87 | - if note_for_main_target?(note) | |
88 | - discussions << [note] | |
89 | - else | |
90 | - discussions << discussion_notes_for(note) | |
91 | - discussion_ids << note.discussion_id | |
92 | - end | |
93 | - end | |
94 | - | |
95 | - discussions | |
96 | - end | |
97 | - | |
98 | - # Helps to distinguish e.g. commit notes in mr notes list | |
99 | - def note_for_main_target?(note) | |
100 | - (@target_type.camelize == note.noteable_type && !note.for_diff_line?) | |
101 | - end | |
102 | -end |
app/controllers/notifications_controller.rb
... | ... | @@ -1,21 +0,0 @@ |
1 | -class NotificationsController < ApplicationController | |
2 | - layout 'profile' | |
3 | - | |
4 | - def show | |
5 | - @notification = current_user.notification | |
6 | - @users_projects = current_user.users_projects | |
7 | - end | |
8 | - | |
9 | - def update | |
10 | - type = params[:notification_type] | |
11 | - | |
12 | - @saved = if type == 'global' | |
13 | - current_user.notification_level = params[:notification_level] | |
14 | - current_user.save | |
15 | - else | |
16 | - users_project = current_user.users_projects.find(params[:notification_id]) | |
17 | - users_project.notification_level = params[:notification_level] | |
18 | - users_project.save | |
19 | - end | |
20 | - end | |
21 | -end |
app/controllers/passwords_controller.rb
... | ... | @@ -1,38 +0,0 @@ |
1 | -class PasswordsController < ApplicationController | |
2 | - layout 'navless' | |
3 | - | |
4 | - skip_before_filter :check_password_expiration | |
5 | - | |
6 | - before_filter :set_user | |
7 | - before_filter :set_title | |
8 | - | |
9 | - def new | |
10 | - end | |
11 | - | |
12 | - def create | |
13 | - new_password = params[:user][:password] | |
14 | - new_password_confirmation = params[:user][:password_confirmation] | |
15 | - | |
16 | - result = @user.update_attributes( | |
17 | - password: new_password, | |
18 | - password_confirmation: new_password_confirmation | |
19 | - ) | |
20 | - | |
21 | - if result | |
22 | - @user.update_attributes(password_expires_at: nil) | |
23 | - redirect_to root_path, notice: 'Password successfully changed' | |
24 | - else | |
25 | - render :new | |
26 | - end | |
27 | - end | |
28 | - | |
29 | - private | |
30 | - | |
31 | - def set_user | |
32 | - @user = current_user | |
33 | - end | |
34 | - | |
35 | - def set_title | |
36 | - @title = "New password" | |
37 | - end | |
38 | -end |
... | ... | @@ -0,0 +1,35 @@ |
1 | +class Profiles::KeysController < ApplicationController | |
2 | + layout "profile" | |
3 | + | |
4 | + def index | |
5 | + @keys = current_user.keys.order('id DESC').all | |
6 | + end | |
7 | + | |
8 | + def show | |
9 | + @key = current_user.keys.find(params[:id]) | |
10 | + end | |
11 | + | |
12 | + def new | |
13 | + @key = current_user.keys.new | |
14 | + end | |
15 | + | |
16 | + def create | |
17 | + @key = current_user.keys.new(params[:key]) | |
18 | + | |
19 | + if @key.save | |
20 | + redirect_to profile_key_path(@key) | |
21 | + else | |
22 | + render 'new' | |
23 | + end | |
24 | + end | |
25 | + | |
26 | + def destroy | |
27 | + @key = current_user.keys.find(params[:id]) | |
28 | + @key.destroy | |
29 | + | |
30 | + respond_to do |format| | |
31 | + format.html { redirect_to profile_keys_url } | |
32 | + format.js { render nothing: true } | |
33 | + end | |
34 | + end | |
35 | +end | ... | ... |
... | ... | @@ -0,0 +1,26 @@ |
1 | +class Profiles::NotificationsController < ApplicationController | |
2 | + layout 'profile' | |
3 | + | |
4 | + def show | |
5 | + @notification = current_user.notification | |
6 | + @users_projects = current_user.users_projects | |
7 | + @users_groups = current_user.users_groups | |
8 | + end | |
9 | + | |
10 | + def update | |
11 | + type = params[:notification_type] | |
12 | + | |
13 | + @saved = if type == 'global' | |
14 | + current_user.notification_level = params[:notification_level] | |
15 | + current_user.save | |
16 | + elsif type == 'group' | |
17 | + users_group = current_user.users_groups.find(params[:notification_id]) | |
18 | + users_group.notification_level = params[:notification_level] | |
19 | + users_group.save | |
20 | + else | |
21 | + users_project = current_user.users_projects.find(params[:notification_id]) | |
22 | + users_project.notification_level = params[:notification_level] | |
23 | + users_project.save | |
24 | + end | |
25 | + end | |
26 | +end | ... | ... |
... | ... | @@ -0,0 +1,38 @@ |
1 | +class Profiles::PasswordsController < ApplicationController | |
2 | + layout 'navless' | |
3 | + | |
4 | + skip_before_filter :check_password_expiration | |
5 | + | |
6 | + before_filter :set_user | |
7 | + before_filter :set_title | |
8 | + | |
9 | + def new | |
10 | + end | |
11 | + | |
12 | + def create | |
13 | + new_password = params[:user][:password] | |
14 | + new_password_confirmation = params[:user][:password_confirmation] | |
15 | + | |
16 | + result = @user.update_attributes( | |
17 | + password: new_password, | |
18 | + password_confirmation: new_password_confirmation | |
19 | + ) | |
20 | + | |
21 | + if result | |
22 | + @user.update_attributes(password_expires_at: nil) | |
23 | + redirect_to root_path, notice: 'Password successfully changed' | |
24 | + else | |
25 | + render :new | |
26 | + end | |
27 | + end | |
28 | + | |
29 | + private | |
30 | + | |
31 | + def set_user | |
32 | + @user = current_user | |
33 | + end | |
34 | + | |
35 | + def set_title | |
36 | + @title = "New password" | |
37 | + end | |
38 | +end | ... | ... |
app/controllers/project_resource_controller.rb
app/controllers/projects/application_controller.rb
... | ... | @@ -0,0 +1,14 @@ |
1 | +# Controller for viewing a file's blame | |
2 | +class Projects::BlameController < Projects::ApplicationController | |
3 | + include ExtractsPath | |
4 | + | |
5 | + # Authorize | |
6 | + before_filter :authorize_read_project! | |
7 | + before_filter :authorize_code_access! | |
8 | + before_filter :require_non_empty_project | |
9 | + | |
10 | + def show | |
11 | + @blob = Gitlab::Git::Blob.new(@repository, @commit.id, @ref, @path) | |
12 | + @blame = Gitlab::Git::Blame.new(project.repository, @commit.id, @path) | |
13 | + end | |
14 | +end | ... | ... |
... | ... | @@ -0,0 +1,13 @@ |
1 | +# Controller for viewing a file's blame | |
2 | +class Projects::BlobController < Projects::ApplicationController | |
3 | + include ExtractsPath | |
4 | + | |
5 | + # Authorize | |
6 | + before_filter :authorize_read_project! | |
7 | + before_filter :authorize_code_access! | |
8 | + before_filter :require_non_empty_project | |
9 | + | |
10 | + def show | |
11 | + @blob = Gitlab::Git::Blob.new(@repository, @commit.id, @ref, @path) | |
12 | + end | |
13 | +end | ... | ... |
... | ... | @@ -0,0 +1,43 @@ |
1 | +# Controller for a specific Commit | |
2 | +# | |
3 | +# Not to be confused with CommitsController, plural. | |
4 | +class Projects::CommitController < Projects::ApplicationController | |
5 | + # Authorize | |
6 | + before_filter :authorize_read_project! | |
7 | + before_filter :authorize_code_access! | |
8 | + before_filter :require_non_empty_project | |
9 | + | |
10 | + def show | |
11 | + result = CommitLoadContext.new(project, current_user, params).execute | |
12 | + | |
13 | + @commit = result[:commit] | |
14 | + | |
15 | + if @commit.nil? | |
16 | + git_not_found! | |
17 | + return | |
18 | + end | |
19 | + | |
20 | + @suppress_diff = result[:suppress_diff] | |
21 | + | |
22 | + @note = result[:note] | |
23 | + @line_notes = result[:line_notes] | |
24 | + @notes_count = result[:notes_count] | |
25 | + @target_type = :commit | |
26 | + @target_id = @commit.id | |
27 | + | |
28 | + @comments_allowed = @reply_allowed = true | |
29 | + @comments_target = { noteable_type: 'Commit', | |
30 | + commit_id: @commit.id } | |
31 | + | |
32 | + respond_to do |format| | |
33 | + format.html do | |
34 | + if result[:status] == :huge_commit | |
35 | + render "huge_commit" and return | |
36 | + end | |
37 | + end | |
38 | + | |
39 | + format.diff { render text: @commit.to_diff } | |
40 | + format.patch { render text: @commit.to_patch } | |
41 | + end | |
42 | + end | |
43 | +end | ... | ... |
... | ... | @@ -0,0 +1,23 @@ |
1 | +require "base64" | |
2 | + | |
3 | +class Projects::CommitsController < Projects::ApplicationController | |
4 | + include ExtractsPath | |
5 | + | |
6 | + # Authorize | |
7 | + before_filter :authorize_read_project! | |
8 | + before_filter :authorize_code_access! | |
9 | + before_filter :require_non_empty_project | |
10 | + | |
11 | + def show | |
12 | + @repo = @project.repository | |
13 | + @limit, @offset = (params[:limit] || 40), (params[:offset] || 0) | |
14 | + | |
15 | + @commits = @repo.commits(@ref, @path, @limit, @offset) | |
16 | + | |
17 | + respond_to do |format| | |
18 | + format.html # index.html.erb | |
19 | + format.js | |
20 | + format.atom { render layout: false } | |
21 | + end | |
22 | + end | |
23 | +end | ... | ... |
... | ... | @@ -0,0 +1,23 @@ |
1 | +class Projects::CompareController < Projects::ApplicationController | |
2 | + # Authorize | |
3 | + before_filter :authorize_read_project! | |
4 | + before_filter :authorize_code_access! | |
5 | + before_filter :require_non_empty_project | |
6 | + | |
7 | + def index | |
8 | + end | |
9 | + | |
10 | + def show | |
11 | + compare = Gitlab::Git::Compare.new(project.repository, params[:from], params[:to]) | |
12 | + | |
13 | + @commits = compare.commits | |
14 | + @commit = compare.commit | |
15 | + @diffs = compare.diffs | |
16 | + @refs_are_same = compare.same | |
17 | + @line_notes = [] | |
18 | + end | |
19 | + | |
20 | + def create | |
21 | + redirect_to project_compare_path(@project, params[:from], params[:to]) | |
22 | + end | |
23 | +end | ... | ... |
... | ... | @@ -0,0 +1,61 @@ |
1 | +class Projects::DeployKeysController < Projects::ApplicationController | |
2 | + respond_to :html | |
3 | + | |
4 | + # Authorize | |
5 | + before_filter :authorize_admin_project! | |
6 | + | |
7 | + layout "project_settings" | |
8 | + | |
9 | + def index | |
10 | + @enabled_keys = @project.deploy_keys.all | |
11 | + @available_keys = available_keys - @enabled_keys | |
12 | + end | |
13 | + | |
14 | + def show | |
15 | + @key = @project.deploy_keys.find(params[:id]) | |
16 | + end | |
17 | + | |
18 | + def new | |
19 | + @key = @project.deploy_keys.new | |
20 | + | |
21 | + respond_with(@key) | |
22 | + end | |
23 | + | |
24 | + def create | |
25 | + @key = DeployKey.new(params[:deploy_key]) | |
26 | + | |
27 | + if @key.valid? && @project.deploy_keys << @key | |
28 | + redirect_to project_deploy_keys_path(@project) | |
29 | + else | |
30 | + render "new" | |
31 | + end | |
32 | + end | |
33 | + | |
34 | + def destroy | |
35 | + @key = @project.deploy_keys.find(params[:id]) | |
36 | + @key.destroy | |
37 | + | |
38 | + respond_to do |format| | |
39 | + format.html { redirect_to project_deploy_keys_url } | |
40 | + format.js { render nothing: true } | |
41 | + end | |
42 | + end | |
43 | + | |
44 | + def enable | |
45 | + project.deploy_keys << available_keys.find(params[:id]) | |
46 | + | |
47 | + redirect_to project_deploy_keys_path(@project) | |
48 | + end | |
49 | + | |
50 | + def disable | |
51 | + @project.deploy_keys_projects.where(deploy_key_id: params[:id]).last.destroy | |
52 | + | |
53 | + redirect_to project_deploy_keys_path(@project) | |
54 | + end | |
55 | + | |
56 | + protected | |
57 | + | |
58 | + def available_keys | |
59 | + @available_keys ||= current_user.accessible_deploy_keys | |
60 | + end | |
61 | +end | ... | ... |
... | ... | @@ -0,0 +1,49 @@ |
1 | +# Controller for edit a repository's file | |
2 | +class Projects::EditTreeController < Projects::ApplicationController | |
3 | + include ExtractsPath | |
4 | + | |
5 | + # Authorize | |
6 | + before_filter :authorize_read_project! | |
7 | + before_filter :authorize_code_access! | |
8 | + before_filter :require_non_empty_project | |
9 | + | |
10 | + before_filter :edit_requirements, only: [:show, :update] | |
11 | + | |
12 | + def show | |
13 | + @last_commit = @project.repository.last_commit_for(@ref, @path).sha | |
14 | + end | |
15 | + | |
16 | + def update | |
17 | + edit_file_action = Gitlab::Satellite::EditFileAction.new(current_user, @project, @ref, @path) | |
18 | + updated_successfully = edit_file_action.commit!( | |
19 | + params[:content], | |
20 | + params[:commit_message], | |
21 | + params[:last_commit] | |
22 | + ) | |
23 | + | |
24 | + if updated_successfully | |
25 | + redirect_to project_blob_path(@project, @id), notice: "Your changes have been successfully commited" | |
26 | + else | |
27 | + flash[:notice] = "Your changes could not be commited, because the file has been changed" | |
28 | + render :show | |
29 | + end | |
30 | + end | |
31 | + | |
32 | + private | |
33 | + | |
34 | + def edit_requirements | |
35 | + @blob = Gitlab::Git::Blob.new(@repository, @commit.id, @ref, @path) | |
36 | + | |
37 | + unless @blob.exists? && @blob.text? | |
38 | + redirect_to project_blob_path(@project, @id), notice: "You can only edit text files" | |
39 | + end | |
40 | + | |
41 | + allowed = if project.protected_branch? @ref | |
42 | + can?(current_user, :push_code_to_protected_branches, project) | |
43 | + else | |
44 | + can?(current_user, :push_code, project) | |
45 | + end | |
46 | + | |
47 | + return access_denied! unless allowed | |
48 | + end | |
49 | +end | ... | ... |
... | ... | @@ -0,0 +1,25 @@ |
1 | +class Projects::GraphsController < Projects::ApplicationController | |
2 | + # Authorize | |
3 | + before_filter :authorize_read_project! | |
4 | + before_filter :authorize_code_access! | |
5 | + before_filter :require_non_empty_project | |
6 | + | |
7 | + def show | |
8 | + respond_to do |format| | |
9 | + format.html | |
10 | + format.js do | |
11 | + fetch_graph | |
12 | + end | |
13 | + end | |
14 | + end | |
15 | + | |
16 | + private | |
17 | + | |
18 | + def fetch_graph | |
19 | + @log = @project.repository.graph_log.to_json | |
20 | + @success = true | |
21 | + rescue => ex | |
22 | + @log = [] | |
23 | + @success = false | |
24 | + end | |
25 | +end | ... | ... |
... | ... | @@ -0,0 +1,39 @@ |
1 | +class Projects::HooksController < Projects::ApplicationController | |
2 | + # Authorize | |
3 | + before_filter :authorize_read_project! | |
4 | + before_filter :authorize_admin_project!, only: [:new, :create, :destroy] | |
5 | + | |
6 | + respond_to :html | |
7 | + | |
8 | + layout "project_settings" | |
9 | + | |
10 | + def index | |
11 | + @hooks = @project.hooks.all | |
12 | + @hook = ProjectHook.new | |
13 | + end | |
14 | + | |
15 | + def create | |
16 | + @hook = @project.hooks.new(params[:hook]) | |
17 | + @hook.save | |
18 | + | |
19 | + if @hook.valid? | |
20 | + redirect_to project_hooks_path(@project) | |
21 | + else | |
22 | + @hooks = @project.hooks.all | |
23 | + render :index | |
24 | + end | |
25 | + end | |
26 | + | |
27 | + def test | |
28 | + TestHookContext.new(project, current_user, params).execute | |
29 | + | |
30 | + redirect_to :back | |
31 | + end | |
32 | + | |
33 | + def destroy | |
34 | + @hook = @project.hooks.find(params[:id]) | |
35 | + @hook.destroy | |
36 | + | |
37 | + redirect_to project_hooks_path(@project) | |
38 | + end | |
39 | +end | ... | ... |
... | ... | @@ -0,0 +1,114 @@ |
1 | +class Projects::IssuesController < Projects::ApplicationController | |
2 | + before_filter :module_enabled | |
3 | + before_filter :issue, only: [:edit, :update, :show] | |
4 | + | |
5 | + # Allow read any issue | |
6 | + before_filter :authorize_read_issue! | |
7 | + | |
8 | + # Allow write(create) issue | |
9 | + before_filter :authorize_write_issue!, only: [:new, :create] | |
10 | + | |
11 | + # Allow modify issue | |
12 | + before_filter :authorize_modify_issue!, only: [:edit, :update] | |
13 | + | |
14 | + respond_to :js, :html | |
15 | + | |
16 | + def index | |
17 | + terms = params['issue_search'] | |
18 | + | |
19 | + @issues = issues_filtered | |
20 | + @issues = @issues.where("title LIKE ?", "%#{terms}%") if terms.present? | |
21 | + @issues = @issues.page(params[:page]).per(20) | |
22 | + | |
23 | + | |
24 | + assignee_id, milestone_id = params[:assignee_id], params[:milestone_id] | |
25 | + | |
26 | + @assignee = @project.team.find(assignee_id) if assignee_id.present? && !assignee_id.to_i.zero? | |
27 | + @milestone = @project.milestones.find(milestone_id) if milestone_id.present? && !milestone_id.to_i.zero? | |
28 | + | |
29 | + respond_to do |format| | |
30 | + format.html # index.html.erb | |
31 | + format.js | |
32 | + format.atom { render layout: false } | |
33 | + end | |
34 | + end | |
35 | + | |
36 | + def new | |
37 | + @issue = @project.issues.new(params[:issue]) | |
38 | + respond_with(@issue) | |
39 | + end | |
40 | + | |
41 | + def edit | |
42 | + respond_with(@issue) | |
43 | + end | |
44 | + | |
45 | + def show | |
46 | + @note = @project.notes.new(noteable: @issue) | |
47 | + @target_type = :issue | |
48 | + @target_id = @issue.id | |
49 | + | |
50 | + respond_to do |format| | |
51 | + format.html | |
52 | + format.js | |
53 | + end | |
54 | + end | |
55 | + | |
56 | + def create | |
57 | + @issue = @project.issues.new(params[:issue]) | |
58 | + @issue.author = current_user | |
59 | + @issue.save | |
60 | + | |
61 | + respond_to do |format| | |
62 | + format.html do | |
63 | + if @issue.valid? | |
64 | + redirect_to project_issue_path(@project, @issue) | |
65 | + else | |
66 | + render :new | |
67 | + end | |
68 | + end | |
69 | + format.js | |
70 | + end | |
71 | + end | |
72 | + | |
73 | + def update | |
74 | + @issue.update_attributes(params[:issue].merge(author_id_of_changes: current_user.id)) | |
75 | + | |
76 | + respond_to do |format| | |
77 | + format.js | |
78 | + format.html do | |
79 | + if @issue.valid? | |
80 | + redirect_to [@project, @issue] | |
81 | + else | |
82 | + render :edit | |
83 | + end | |
84 | + end | |
85 | + end | |
86 | + end | |
87 | + | |
88 | + def bulk_update | |
89 | + result = Issues::BulkUpdateContext.new(project, current_user, params).execute | |
90 | + redirect_to :back, notice: "#{result[:count]} issues updated" | |
91 | + end | |
92 | + | |
93 | + protected | |
94 | + | |
95 | + def issue | |
96 | + @issue ||= @project.issues.find(params[:id]) | |
97 | + end | |
98 | + | |
99 | + def authorize_modify_issue! | |
100 | + return render_404 unless can?(current_user, :modify_issue, @issue) | |
101 | + end | |
102 | + | |
103 | + def authorize_admin_issue! | |
104 | + return render_404 unless can?(current_user, :admin_issue, @issue) | |
105 | + end | |
106 | + | |
107 | + def module_enabled | |
108 | + return render_404 unless @project.issues_enabled | |
109 | + end | |
110 | + | |
111 | + def issues_filtered | |
112 | + @issues = Issues::ListContext.new(project, current_user, params).execute | |
113 | + end | |
114 | +end | ... | ... |
... | ... | @@ -0,0 +1,24 @@ |
1 | +class Projects::LabelsController < Projects::ApplicationController | |
2 | + before_filter :module_enabled | |
3 | + | |
4 | + # Allow read any issue | |
5 | + before_filter :authorize_read_issue! | |
6 | + | |
7 | + respond_to :js, :html | |
8 | + | |
9 | + def index | |
10 | + @labels = @project.issues_labels | |
11 | + end | |
12 | + | |
13 | + def generate | |
14 | + Gitlab::IssuesLabels.generate(@project) | |
15 | + | |
16 | + redirect_to project_labels_path(@project) | |
17 | + end | |
18 | + | |
19 | + protected | |
20 | + | |
21 | + def module_enabled | |
22 | + return render_404 unless @project.issues_enabled | |
23 | + end | |
24 | +end | ... | ... |
... | ... | @@ -0,0 +1,162 @@ |
1 | +require 'gitlab/satellite/satellite' | |
2 | + | |
3 | +class Projects::MergeRequestsController < Projects::ApplicationController | |
4 | + before_filter :module_enabled | |
5 | + before_filter :merge_request, only: [:edit, :update, :show, :commits, :diffs, :automerge, :automerge_check, :ci_status] | |
6 | + before_filter :validates_merge_request, only: [:show, :diffs] | |
7 | + before_filter :define_show_vars, only: [:show, :diffs] | |
8 | + | |
9 | + # Allow read any merge_request | |
10 | + before_filter :authorize_read_merge_request! | |
11 | + | |
12 | + # Allow write(create) merge_request | |
13 | + before_filter :authorize_write_merge_request!, only: [:new, :create] | |
14 | + | |
15 | + # Allow modify merge_request | |
16 | + before_filter :authorize_modify_merge_request!, only: [:close, :edit, :update, :sort] | |
17 | + | |
18 | + def index | |
19 | + @merge_requests = MergeRequestsLoadContext.new(project, current_user, params).execute | |
20 | + end | |
21 | + | |
22 | + def show | |
23 | + respond_to do |format| | |
24 | + format.html | |
25 | + format.js | |
26 | + | |
27 | + format.diff { render text: @merge_request.to_diff } | |
28 | + format.patch { render text: @merge_request.to_patch } | |
29 | + end | |
30 | + end | |
31 | + | |
32 | + def diffs | |
33 | + @commit = @merge_request.last_commit | |
34 | + | |
35 | + @comments_allowed = @reply_allowed = true | |
36 | + @comments_target = { noteable_type: 'MergeRequest', | |
37 | + noteable_id: @merge_request.id } | |
38 | + @line_notes = @merge_request.notes.where("line_code is not null") | |
39 | + end | |
40 | + | |
41 | + def new | |
42 | + @merge_request = @project.merge_requests.new(params[:merge_request]) | |
43 | + end | |
44 | + | |
45 | + def edit | |
46 | + end | |
47 | + | |
48 | + def create | |
49 | + @merge_request = @project.merge_requests.new(params[:merge_request]) | |
50 | + @merge_request.author = current_user | |
51 | + | |
52 | + if @merge_request.save | |
53 | + @merge_request.reload_code | |
54 | + redirect_to [@project, @merge_request], notice: 'Merge request was successfully created.' | |
55 | + else | |
56 | + render "new" | |
57 | + end | |
58 | + end | |
59 | + | |
60 | + def update | |
61 | + if @merge_request.update_attributes(params[:merge_request].merge(author_id_of_changes: current_user.id)) | |
62 | + @merge_request.reload_code | |
63 | + @merge_request.mark_as_unchecked | |
64 | + redirect_to [@project, @merge_request], notice: 'Merge request was successfully updated.' | |
65 | + else | |
66 | + render "edit" | |
67 | + end | |
68 | + end | |
69 | + | |
70 | + def automerge_check | |
71 | + if @merge_request.unchecked? | |
72 | + @merge_request.check_if_can_be_merged | |
73 | + end | |
74 | + render json: {merge_status: @merge_request.merge_status_name} | |
75 | + rescue Gitlab::SatelliteNotExistError | |
76 | + render json: {merge_status: :no_satellite} | |
77 | + end | |
78 | + | |
79 | + def automerge | |
80 | + return access_denied! unless allowed_to_merge? | |
81 | + | |
82 | + if @merge_request.opened? && @merge_request.can_be_merged? | |
83 | + @merge_request.should_remove_source_branch = params[:should_remove_source_branch] | |
84 | + @merge_request.automerge!(current_user) | |
85 | + @status = true | |
86 | + else | |
87 | + @status = false | |
88 | + end | |
89 | + end | |
90 | + | |
91 | + def branch_from | |
92 | + @commit = @repository.commit(params[:ref]) | |
93 | + end | |
94 | + | |
95 | + def branch_to | |
96 | + @commit = @repository.commit(params[:ref]) | |
97 | + end | |
98 | + | |
99 | + def ci_status | |
100 | + status = project.gitlab_ci_service.commit_status(merge_request.last_commit.sha) | |
101 | + response = { status: status } | |
102 | + | |
103 | + render json: response | |
104 | + end | |
105 | + | |
106 | + protected | |
107 | + | |
108 | + def merge_request | |
109 | + @merge_request ||= @project.merge_requests.find(params[:id]) | |
110 | + end | |
111 | + | |
112 | + def authorize_modify_merge_request! | |
113 | + return render_404 unless can?(current_user, :modify_merge_request, @merge_request) | |
114 | + end | |
115 | + | |
116 | + def authorize_admin_merge_request! | |
117 | + return render_404 unless can?(current_user, :admin_merge_request, @merge_request) | |
118 | + end | |
119 | + | |
120 | + def module_enabled | |
121 | + return render_404 unless @project.merge_requests_enabled | |
122 | + end | |
123 | + | |
124 | + def validates_merge_request | |
125 | + # Show git not found page if target branch doesn't exist | |
126 | + return invalid_mr unless @project.repository.branch_names.include?(@merge_request.target_branch) | |
127 | + | |
128 | + # Show git not found page if source branch doesn't exist | |
129 | + # and there is no saved commits between source & target branch | |
130 | + return invalid_mr if !@project.repository.branch_names.include?(@merge_request.source_branch) && @merge_request.commits.blank? | |
131 | + end | |
132 | + | |
133 | + def define_show_vars | |
134 | + # Build a note object for comment form | |
135 | + @note = @project.notes.new(noteable: @merge_request) | |
136 | + | |
137 | + # Get commits from repository | |
138 | + # or from cache if already merged | |
139 | + @commits = @merge_request.commits | |
140 | + | |
141 | + @allowed_to_merge = allowed_to_merge? | |
142 | + @show_merge_controls = @merge_request.opened? && @commits.any? && @allowed_to_merge | |
143 | + | |
144 | + @target_type = :merge_request | |
145 | + @target_id = @merge_request.id | |
146 | + end | |
147 | + | |
148 | + def allowed_to_merge? | |
149 | + action = if project.protected_branch?(@merge_request.target_branch) | |
150 | + :push_code_to_protected_branches | |
151 | + else | |
152 | + :push_code | |
153 | + end | |
154 | + | |
155 | + can?(current_user, action, @project) | |
156 | + end | |
157 | + | |
158 | + def invalid_mr | |
159 | + # Render special view for MR with removed source or target branch | |
160 | + render 'invalid' | |
161 | + end | |
162 | +end | ... | ... |
... | ... | @@ -0,0 +1,94 @@ |
1 | +class Projects::MilestonesController < Projects::ApplicationController | |
2 | + before_filter :module_enabled | |
3 | + before_filter :milestone, only: [:edit, :update, :destroy, :show] | |
4 | + | |
5 | + # Allow read any milestone | |
6 | + before_filter :authorize_read_milestone! | |
7 | + | |
8 | + # Allow admin milestone | |
9 | + before_filter :authorize_admin_milestone!, except: [:index, :show] | |
10 | + | |
11 | + respond_to :html | |
12 | + | |
13 | + def index | |
14 | + @milestones = case params[:f] | |
15 | + when 'all'; @project.milestones.order("state, due_date DESC") | |
16 | + when 'closed'; @project.milestones.closed.order("due_date DESC") | |
17 | + else @project.milestones.active.order("due_date DESC") | |
18 | + end | |
19 | + | |
20 | + @milestones = @milestones.includes(:project) | |
21 | + @milestones = @milestones.page(params[:page]).per(20) | |
22 | + end | |
23 | + | |
24 | + def new | |
25 | + @milestone = @project.milestones.new | |
26 | + respond_with(@milestone) | |
27 | + end | |
28 | + | |
29 | + def edit | |
30 | + respond_with(@milestone) | |
31 | + end | |
32 | + | |
33 | + def show | |
34 | + @issues = @milestone.issues | |
35 | + @users = @milestone.participants.uniq | |
36 | + @merge_requests = @milestone.merge_requests | |
37 | + | |
38 | + respond_to do |format| | |
39 | + format.html | |
40 | + format.js | |
41 | + end | |
42 | + end | |
43 | + | |
44 | + def create | |
45 | + @milestone = @project.milestones.new(params[:milestone]) | |
46 | + @milestone.author_id_of_changes = current_user.id | |
47 | + | |
48 | + if @milestone.save | |
49 | + redirect_to project_milestone_path(@project, @milestone) | |
50 | + else | |
51 | + render "new" | |
52 | + end | |
53 | + end | |
54 | + | |
55 | + def update | |
56 | + @milestone.update_attributes(params[:milestone].merge(author_id_of_changes: current_user.id)) | |
57 | + | |
58 | + respond_to do |format| | |
59 | + format.js | |
60 | + format.html do | |
61 | + if @milestone.valid? | |
62 | + redirect_to [@project, @milestone] | |
63 | + else | |
64 | + render :edit | |
65 | + end | |
66 | + end | |
67 | + end | |
68 | + end | |
69 | + | |
70 | + def destroy | |
71 | + return access_denied! unless can?(current_user, :admin_milestone, @milestone) | |
72 | + | |
73 | + @milestone.destroy | |
74 | + | |
75 | + respond_to do |format| | |
76 | + format.html { redirect_to project_milestones_path } | |
77 | + format.js { render nothing: true } | |
78 | + end | |
79 | + end | |
80 | + | |
81 | + protected | |
82 | + | |
83 | + def milestone | |
84 | + @milestone ||= @project.milestones.find(params[:id]) | |
85 | + end | |
86 | + | |
87 | + def authorize_admin_milestone! | |
88 | + return render_404 unless can?(current_user, :admin_milestone, @project) | |
89 | + end | |
90 | + | |
91 | + def module_enabled | |
92 | + return render_404 unless @project.issues_enabled | |
93 | + end | |
94 | +end | ... | ... |
... | ... | @@ -0,0 +1,23 @@ |
1 | +class Projects::NetworkController < Projects::ApplicationController | |
2 | + include ExtractsPath | |
3 | + include ApplicationHelper | |
4 | + | |
5 | + # Authorize | |
6 | + before_filter :authorize_read_project! | |
7 | + before_filter :authorize_code_access! | |
8 | + before_filter :require_non_empty_project | |
9 | + | |
10 | + def show | |
11 | + if @options[:q] | |
12 | + @commit = @project.repository.commit(@options[:q]) || @commit | |
13 | + end | |
14 | + | |
15 | + respond_to do |format| | |
16 | + format.html | |
17 | + | |
18 | + format.json do | |
19 | + @graph = Network::Graph.new(project, @ref, @commit, @options[:filter_ref]) | |
20 | + end | |
21 | + end | |
22 | + end | |
23 | +end | ... | ... |
... | ... | @@ -0,0 +1,102 @@ |
1 | +class Projects::NotesController < Projects::ApplicationController | |
2 | + # Authorize | |
3 | + before_filter :authorize_read_note! | |
4 | + before_filter :authorize_write_note!, only: [:create] | |
5 | + | |
6 | + respond_to :js | |
7 | + | |
8 | + def index | |
9 | + @notes = Notes::LoadContext.new(project, current_user, params).execute | |
10 | + @target_type = params[:target_type].camelize | |
11 | + @target_id = params[:target_id] | |
12 | + | |
13 | + if params[:target_type] == "merge_request" | |
14 | + @discussions = discussions_from_notes | |
15 | + end | |
16 | + | |
17 | + respond_with(@notes) | |
18 | + end | |
19 | + | |
20 | + def create | |
21 | + @note = Notes::CreateContext.new(project, current_user, params).execute | |
22 | + @target_type = params[:target_type].camelize | |
23 | + @target_id = params[:target_id] | |
24 | + | |
25 | + respond_to do |format| | |
26 | + format.html {redirect_to :back} | |
27 | + format.js | |
28 | + end | |
29 | + end | |
30 | + | |
31 | + def destroy | |
32 | + @note = @project.notes.find(params[:id]) | |
33 | + return access_denied! unless can?(current_user, :admin_note, @note) | |
34 | + @note.destroy | |
35 | + | |
36 | + respond_to do |format| | |
37 | + format.js { render nothing: true } | |
38 | + end | |
39 | + end | |
40 | + | |
41 | + def update | |
42 | + @note = @project.notes.find(params[:id]) | |
43 | + return access_denied! unless can?(current_user, :admin_note, @note) | |
44 | + | |
45 | + @note.update_attributes(params[:note]) | |
46 | + | |
47 | + respond_to do |format| | |
48 | + format.js do | |
49 | + render js: { success: @note.valid?, id: @note.id, note: view_context.markdown(@note.note) }.to_json | |
50 | + end | |
51 | + format.html do | |
52 | + redirect_to :back | |
53 | + end | |
54 | + end | |
55 | + end | |
56 | + | |
57 | + def delete_attachment | |
58 | + @note = @project.notes.find(params[:id]) | |
59 | + @note.remove_attachment! | |
60 | + @note.update_attribute(:attachment, nil) | |
61 | + | |
62 | + respond_to do |format| | |
63 | + format.js { render nothing: true } | |
64 | + end | |
65 | + end | |
66 | + | |
67 | + def preview | |
68 | + render text: view_context.markdown(params[:note]) | |
69 | + end | |
70 | + | |
71 | + protected | |
72 | + | |
73 | + def discussion_notes_for(note) | |
74 | + @notes.select do |other_note| | |
75 | + note.discussion_id == other_note.discussion_id | |
76 | + end | |
77 | + end | |
78 | + | |
79 | + def discussions_from_notes | |
80 | + discussion_ids = [] | |
81 | + discussions = [] | |
82 | + | |
83 | + @notes.each do |note| | |
84 | + next if discussion_ids.include?(note.discussion_id) | |
85 | + | |
86 | + # don't group notes for the main target | |
87 | + if note_for_main_target?(note) | |
88 | + discussions << [note] | |
89 | + else | |
90 | + discussions << discussion_notes_for(note) | |
91 | + discussion_ids << note.discussion_id | |
92 | + end | |
93 | + end | |
94 | + | |
95 | + discussions | |
96 | + end | |
97 | + | |
98 | + # Helps to distinguish e.g. commit notes in mr notes list | |
99 | + def note_for_main_target?(note) | |
100 | + (@target_type.camelize == note.noteable_type && !note.for_diff_line?) | |
101 | + end | |
102 | +end | ... | ... |
app/controllers/projects/protected_branches_controller.rb
0 → 100644
... | ... | @@ -0,0 +1,26 @@ |
1 | +class Projects::ProtectedBranchesController < Projects::ApplicationController | |
2 | + # Authorize | |
3 | + before_filter :authorize_read_project! | |
4 | + before_filter :require_non_empty_project | |
5 | + | |
6 | + before_filter :authorize_admin_project!, only: [:destroy, :create] | |
7 | + | |
8 | + def index | |
9 | + @branches = @project.protected_branches.all | |
10 | + @protected_branch = @project.protected_branches.new | |
11 | + end | |
12 | + | |
13 | + def create | |
14 | + @project.protected_branches.create(params[:protected_branch]) | |
15 | + redirect_to project_protected_branches_path(@project) | |
16 | + end | |
17 | + | |
18 | + def destroy | |
19 | + @project.protected_branches.find(params[:id]).destroy | |
20 | + | |
21 | + respond_to do |format| | |
22 | + format.html { redirect_to project_protected_branches_path } | |
23 | + format.js { render nothing: true } | |
24 | + end | |
25 | + end | |
26 | +end | ... | ... |
... | ... | @@ -0,0 +1,25 @@ |
1 | +# Controller for viewing a file's raw | |
2 | +class Projects::RawController < Projects::ApplicationController | |
3 | + include ExtractsPath | |
4 | + | |
5 | + # Authorize | |
6 | + before_filter :authorize_read_project! | |
7 | + before_filter :authorize_code_access! | |
8 | + before_filter :require_non_empty_project | |
9 | + | |
10 | + def show | |
11 | + @blob = Gitlab::Git::Blob.new(@repository, @commit.id, @ref, @path) | |
12 | + | |
13 | + if @blob.exists? | |
14 | + send_data( | |
15 | + @blob.data, | |
16 | + type: @blob.mime_type, | |
17 | + disposition: 'inline', | |
18 | + filename: @blob.name | |
19 | + ) | |
20 | + else | |
21 | + not_found! | |
22 | + end | |
23 | + end | |
24 | +end | |
25 | + | ... | ... |
... | ... | @@ -0,0 +1,43 @@ |
1 | +class Projects::RefsController < Projects::ApplicationController | |
2 | + include ExtractsPath | |
3 | + | |
4 | + # Authorize | |
5 | + before_filter :authorize_read_project! | |
6 | + before_filter :authorize_code_access! | |
7 | + before_filter :require_non_empty_project | |
8 | + | |
9 | + def switch | |
10 | + respond_to do |format| | |
11 | + format.html do | |
12 | + new_path = if params[:destination] == "tree" | |
13 | + project_tree_path(@project, (@id)) | |
14 | + elsif params[:destination] == "blob" | |
15 | + project_blob_path(@project, (@id)) | |
16 | + elsif params[:destination] == "graph" | |
17 | + project_network_path(@project, @id, @options) | |
18 | + else | |
19 | + project_commits_path(@project, @id) | |
20 | + end | |
21 | + | |
22 | + redirect_to new_path | |
23 | + end | |
24 | + format.js do | |
25 | + @ref = params[:ref] | |
26 | + define_tree_vars | |
27 | + render "tree" | |
28 | + end | |
29 | + end | |
30 | + end | |
31 | + | |
32 | + def logs_tree | |
33 | + contents = @tree.entries | |
34 | + @logs = contents.map do |content| | |
35 | + file = params[:path] ? File.join(params[:path], content.name) : content.name | |
36 | + last_commit = @repo.commits(@commit.id, file, 1).last | |
37 | + { | |
38 | + file_name: content.name, | |
39 | + commit: last_commit | |
40 | + } | |
41 | + end | |
42 | + end | |
43 | +end | ... | ... |
... | ... | @@ -0,0 +1,41 @@ |
1 | +class Projects::RepositoriesController < Projects::ApplicationController | |
2 | + # Authorize | |
3 | + before_filter :authorize_read_project! | |
4 | + before_filter :authorize_code_access! | |
5 | + before_filter :require_non_empty_project | |
6 | + | |
7 | + def show | |
8 | + @activities = @repository.commits_with_refs(20) | |
9 | + end | |
10 | + | |
11 | + def branches | |
12 | + @branches = @repository.branches | |
13 | + end | |
14 | + | |
15 | + def tags | |
16 | + @tags = @repository.tags | |
17 | + end | |
18 | + | |
19 | + def stats | |
20 | + @stats = Gitlab::Git::Stats.new(@repository.raw, @repository.root_ref) | |
21 | + @graph = @stats.graph | |
22 | + end | |
23 | + | |
24 | + def archive | |
25 | + unless can?(current_user, :download_code, @project) | |
26 | + render_404 and return | |
27 | + end | |
28 | + | |
29 | + | |
30 | + storage_path = Rails.root.join("tmp", "repositories") | |
31 | + | |
32 | + file_path = @repository.archive_repo(params[:ref], storage_path) | |
33 | + | |
34 | + if file_path | |
35 | + # Send file to user | |
36 | + send_file file_path | |
37 | + else | |
38 | + render_404 | |
39 | + end | |
40 | + end | |
41 | +end | ... | ... |
... | ... | @@ -0,0 +1,39 @@ |
1 | +class Projects::ServicesController < Projects::ApplicationController | |
2 | + # Authorize | |
3 | + before_filter :authorize_admin_project! | |
4 | + before_filter :service, only: [:edit, :update, :test] | |
5 | + | |
6 | + respond_to :html | |
7 | + | |
8 | + layout "project_settings" | |
9 | + | |
10 | + def index | |
11 | + @project.build_missing_services | |
12 | + @services = @project.services.reload | |
13 | + end | |
14 | + | |
15 | + def edit | |
16 | + end | |
17 | + | |
18 | + def update | |
19 | + if @service.update_attributes(params[:service]) | |
20 | + redirect_to edit_project_service_path(@project, @service.to_param) | |
21 | + else | |
22 | + render 'edit' | |
23 | + end | |
24 | + end | |
25 | + | |
26 | + def test | |
27 | + data = GitPushService.new.sample_data(project, current_user) | |
28 | + | |
29 | + @service.execute(data) | |
30 | + | |
31 | + redirect_to :back | |
32 | + end | |
33 | + | |
34 | + private | |
35 | + | |
36 | + def service | |
37 | + @service ||= @project.services.find { |service| service.to_param == params[:id] } | |
38 | + end | |
39 | +end | ... | ... |
app/controllers/projects/snippets_controller.rb
... | ... | @@ -14,7 +14,7 @@ class Projects::SnippetsController < Projects::ApplicationController |
14 | 14 | # Allow destroy snippet |
15 | 15 | before_filter :authorize_admin_project_snippet!, only: [:destroy] |
16 | 16 | |
17 | - layout 'project_resource' | |
17 | + layout 'projects' | |
18 | 18 | |
19 | 19 | respond_to :html |
20 | 20 | ... | ... |
... | ... | @@ -0,0 +1,62 @@ |
1 | +class Projects::TeamMembersController < Projects::ApplicationController | |
2 | + # Authorize | |
3 | + before_filter :authorize_read_project! | |
4 | + before_filter :authorize_admin_project!, except: [:index, :show] | |
5 | + | |
6 | + layout "project_settings" | |
7 | + | |
8 | + def index | |
9 | + @group = @project.group | |
10 | + @users_projects = @project.users_projects.order('project_access DESC') | |
11 | + end | |
12 | + | |
13 | + def new | |
14 | + @user_project_relation = project.users_projects.new | |
15 | + end | |
16 | + | |
17 | + def create | |
18 | + users = User.where(id: params[:user_ids].split(',')) | |
19 | + | |
20 | + @project.team << [users, params[:project_access]] | |
21 | + | |
22 | + if params[:redirect_to] | |
23 | + redirect_to params[:redirect_to] | |
24 | + else | |
25 | + redirect_to project_team_index_path(@project) | |
26 | + end | |
27 | + end | |
28 | + | |
29 | + def update | |
30 | + @user_project_relation = project.users_projects.find_by_user_id(member) | |
31 | + @user_project_relation.update_attributes(params[:team_member]) | |
32 | + | |
33 | + unless @user_project_relation.valid? | |
34 | + flash[:alert] = "User should have at least one role" | |
35 | + end | |
36 | + redirect_to project_team_index_path(@project) | |
37 | + end | |
38 | + | |
39 | + def destroy | |
40 | + @user_project_relation = project.users_projects.find_by_user_id(member) | |
41 | + @user_project_relation.destroy | |
42 | + | |
43 | + respond_to do |format| | |
44 | + format.html { redirect_to project_team_index_path(@project) } | |
45 | + format.js { render nothing: true } | |
46 | + end | |
47 | + end | |
48 | + | |
49 | + def apply_import | |
50 | + giver = Project.find(params[:source_project_id]) | |
51 | + status = @project.team.import(giver) | |
52 | + notice = status ? "Succesfully imported" : "Import failed" | |
53 | + | |
54 | + redirect_to project_team_index_path(project), notice: notice | |
55 | + end | |
56 | + | |
57 | + protected | |
58 | + | |
59 | + def member | |
60 | + @member ||= User.find_by_username(params[:id]) | |
61 | + end | |
62 | +end | ... | ... |
app/controllers/projects/teams_controller.rb
... | ... | @@ -1,34 +0,0 @@ |
1 | -class Projects::TeamsController < Projects::ApplicationController | |
2 | - | |
3 | - before_filter :authorize_admin_team_member! | |
4 | - | |
5 | - def available | |
6 | - @teams = current_user.is_admin? ? UserTeam.scoped : current_user.user_teams | |
7 | - @teams = @teams.without_project(project) | |
8 | - unless @teams.any? | |
9 | - redirect_to project_team_index_path(project), notice: "No available teams for assigment." | |
10 | - end | |
11 | - end | |
12 | - | |
13 | - def assign | |
14 | - unless params[:team_id].blank? | |
15 | - team = UserTeam.find(params[:team_id]) | |
16 | - access = params[:greatest_project_access] | |
17 | - team.assign_to_project(project, access) | |
18 | - end | |
19 | - redirect_to project_team_index_path(project) | |
20 | - end | |
21 | - | |
22 | - def resign | |
23 | - team = project.user_teams.find_by_path(params[:id]) | |
24 | - team.resign_from_project(project) | |
25 | - | |
26 | - redirect_to project_team_index_path(project) | |
27 | - end | |
28 | - | |
29 | - protected | |
30 | - | |
31 | - def user_team | |
32 | - @team ||= UserTeam.find_by_path(params[:id]) | |
33 | - end | |
34 | -end |
... | ... | @@ -0,0 +1,17 @@ |
1 | +# Controller for viewing a repository's file structure | |
2 | +class Projects::TreeController < Projects::ApplicationController | |
3 | + include ExtractsPath | |
4 | + | |
5 | + # Authorize | |
6 | + before_filter :authorize_read_project! | |
7 | + before_filter :authorize_code_access! | |
8 | + before_filter :require_non_empty_project | |
9 | + | |
10 | + def show | |
11 | + respond_to do |format| | |
12 | + format.html | |
13 | + # Disable cache so browser history works | |
14 | + format.js { no_cache_headers } | |
15 | + end | |
16 | + end | |
17 | +end | ... | ... |
... | ... | @@ -0,0 +1,20 @@ |
1 | +class Projects::WallsController < Projects::ApplicationController | |
2 | + before_filter :module_enabled | |
3 | + | |
4 | + respond_to :js, :html | |
5 | + | |
6 | + def show | |
7 | + @note = @project.notes.new | |
8 | + | |
9 | + respond_to do |format| | |
10 | + format.html | |
11 | + end | |
12 | + end | |
13 | + | |
14 | + protected | |
15 | + | |
16 | + def module_enabled | |
17 | + return render_404 unless @project.wall_enabled | |
18 | + end | |
19 | +end | |
20 | + | ... | ... |
... | ... | @@ -0,0 +1,95 @@ |
1 | +class Projects::WikisController < Projects::ApplicationController | |
2 | + before_filter :authorize_read_wiki! | |
3 | + before_filter :authorize_write_wiki!, only: [:edit, :create, :history] | |
4 | + before_filter :authorize_admin_wiki!, only: :destroy | |
5 | + before_filter :load_gollum_wiki | |
6 | + | |
7 | + def pages | |
8 | + @wiki_pages = @gollum_wiki.pages | |
9 | + end | |
10 | + | |
11 | + def show | |
12 | + @wiki = @gollum_wiki.find_page(params[:id], params[:version_id]) | |
13 | + | |
14 | + if @wiki | |
15 | + render 'show' | |
16 | + else | |
17 | + return render('empty') unless can?(current_user, :write_wiki, @project) | |
18 | + @wiki = WikiPage.new(@gollum_wiki) | |
19 | + @wiki.title = params[:id] | |
20 | + | |
21 | + render 'edit' | |
22 | + end | |
23 | + end | |
24 | + | |
25 | + def edit | |
26 | + @wiki = @gollum_wiki.find_page(params[:id]) | |
27 | + end | |
28 | + | |
29 | + def update | |
30 | + @wiki = @gollum_wiki.find_page(params[:id]) | |
31 | + | |
32 | + return render('empty') unless can?(current_user, :write_wiki, @project) | |
33 | + | |
34 | + if @wiki.update(content, format, message) | |
35 | + redirect_to [@project, @wiki], notice: 'Wiki was successfully updated.' | |
36 | + else | |
37 | + render 'edit' | |
38 | + end | |
39 | + end | |
40 | + | |
41 | + def create | |
42 | + @wiki = WikiPage.new(@gollum_wiki) | |
43 | + | |
44 | + if @wiki.create(wiki_params) | |
45 | + redirect_to project_wiki_path(@project, @wiki), notice: 'Wiki was successfully updated.' | |
46 | + else | |
47 | + render action: "edit" | |
48 | + end | |
49 | + end | |
50 | + | |
51 | + def history | |
52 | + @wiki = @gollum_wiki.find_page(params[:id]) | |
53 | + | |
54 | + redirect_to(project_wiki_path(@project, :home), notice: "Page not found") unless @wiki | |
55 | + end | |
56 | + | |
57 | + def destroy | |
58 | + @wiki = @gollum_wiki.find_page(params[:id]) | |
59 | + @wiki.delete if @wiki | |
60 | + redirect_to project_wiki_path(@project, :home), notice: "Page was successfully deleted" | |
61 | + end | |
62 | + | |
63 | + def git_access | |
64 | + end | |
65 | + | |
66 | + private | |
67 | + | |
68 | + def load_gollum_wiki | |
69 | + @gollum_wiki = GollumWiki.new(@project, current_user) | |
70 | + | |
71 | + # Call #wiki to make sure the Wiki Repo is initialized | |
72 | + @gollum_wiki.wiki | |
73 | + rescue GollumWiki::CouldNotCreateWikiError => ex | |
74 | + flash[:notice] = "Could not create Wiki Repository at this time. Please try again later." | |
75 | + redirect_to @project | |
76 | + return false | |
77 | + end | |
78 | + | |
79 | + def wiki_params | |
80 | + params[:wiki].slice(:title, :content, :format, :message) | |
81 | + end | |
82 | + | |
83 | + def content | |
84 | + params[:wiki][:content] | |
85 | + end | |
86 | + | |
87 | + def format | |
88 | + params[:wiki][:format] | |
89 | + end | |
90 | + | |
91 | + def message | |
92 | + params[:wiki][:message] | |
93 | + end | |
94 | + | |
95 | +end | ... | ... |
app/controllers/projects_controller.rb
1 | -class ProjectsController < ProjectResourceController | |
1 | +class ProjectsController < Projects::ApplicationController | |
2 | 2 | skip_before_filter :project, only: [:new, :create] |
3 | 3 | skip_before_filter :repository, only: [:new, :create] |
4 | 4 | |
... | ... | @@ -15,6 +15,7 @@ class ProjectsController < ProjectResourceController |
15 | 15 | end |
16 | 16 | |
17 | 17 | def edit |
18 | + render 'edit', layout: "project_settings" | |
18 | 19 | end |
19 | 20 | |
20 | 21 | def create |
... | ... | @@ -26,7 +27,7 @@ class ProjectsController < ProjectResourceController |
26 | 27 | if @project.saved? |
27 | 28 | redirect_to @project |
28 | 29 | else |
29 | - render action: "new" | |
30 | + render "new" | |
30 | 31 | end |
31 | 32 | end |
32 | 33 | format.js |
... | ... | @@ -42,7 +43,7 @@ class ProjectsController < ProjectResourceController |
42 | 43 | format.html { redirect_to edit_project_path(@project), notice: 'Project was successfully updated.' } |
43 | 44 | format.js |
44 | 45 | else |
45 | - format.html { render action: "edit" } | |
46 | + format.html { render "edit", layout: "project_settings" } | |
46 | 47 | format.js |
47 | 48 | end |
48 | 49 | end |
... | ... | @@ -89,7 +90,7 @@ class ProjectsController < ProjectResourceController |
89 | 90 | redirect_to(@forked_project, notice: 'Project was successfully forked.') |
90 | 91 | else |
91 | 92 | @title = 'Fork project' |
92 | - render action: "fork" | |
93 | + render "fork" | |
93 | 94 | end |
94 | 95 | end |
95 | 96 | format.js |
... | ... | @@ -100,7 +101,7 @@ class ProjectsController < ProjectResourceController |
100 | 101 | @suggestions = { |
101 | 102 | emojis: Emoji.names, |
102 | 103 | issues: @project.issues.select([:id, :title, :description]), |
103 | - members: @project.users.select([:username, :name]).order(:username) | |
104 | + members: @project.team.members.sort_by(&:username).map { |user| { username: user.username, name: user.name } } | |
104 | 105 | } |
105 | 106 | |
106 | 107 | respond_to do |format| | ... | ... |
app/controllers/protected_branches_controller.rb
... | ... | @@ -1,26 +0,0 @@ |
1 | -class ProtectedBranchesController < ProjectResourceController | |
2 | - # Authorize | |
3 | - before_filter :authorize_read_project! | |
4 | - before_filter :require_non_empty_project | |
5 | - | |
6 | - before_filter :authorize_admin_project!, only: [:destroy, :create] | |
7 | - | |
8 | - def index | |
9 | - @branches = @project.protected_branches.all | |
10 | - @protected_branch = @project.protected_branches.new | |
11 | - end | |
12 | - | |
13 | - def create | |
14 | - @project.protected_branches.create(params[:protected_branch]) | |
15 | - redirect_to project_protected_branches_path(@project) | |
16 | - end | |
17 | - | |
18 | - def destroy | |
19 | - @project.protected_branches.find(params[:id]).destroy | |
20 | - | |
21 | - respond_to do |format| | |
22 | - format.html { redirect_to project_protected_branches_path } | |
23 | - format.js { render nothing: true } | |
24 | - end | |
25 | - end | |
26 | -end |