Commit 251df827a5308d483a95242970569075ab655703
1 parent
5221dbfe
Exists in
spb-stable
and in
3 other branches
added group avatars
Showing
15 changed files
with
161 additions
and
2 deletions
Show diff stats
704 Bytes
app/assets/javascripts/groups.js.coffee
| ... | ... | @@ -4,3 +4,14 @@ class GroupMembers |
| 4 | 4 | $(this).fadeOut() |
| 5 | 5 | |
| 6 | 6 | @GroupMembers = GroupMembers |
| 7 | + | |
| 8 | +$ -> | |
| 9 | + # avatar | |
| 10 | + $('.js-choose-group-avatar-button').bind "click", -> | |
| 11 | + form = $(this).closest("form") | |
| 12 | + form.find(".js-group-avatar-input").click() | |
| 13 | + | |
| 14 | + $('.js-group-avatar-input').bind "change", -> | |
| 15 | + form = $(this).closest("form") | |
| 16 | + filename = $(this).val().replace(/^.*[\\\/]/, '') | |
| 17 | + form.find(".js-avatar-filename").text(filename) | |
| 7 | 18 | \ No newline at end of file | ... | ... |
app/helpers/application_helper.rb
| ... | ... | @@ -49,6 +49,15 @@ module ApplicationHelper |
| 49 | 49 | args.any? { |v| v.to_s.downcase == action_name } |
| 50 | 50 | end |
| 51 | 51 | |
| 52 | + def group_icon(group_path) | |
| 53 | + group = Group.find_by(path: group_path) | |
| 54 | + if group && group.avatar.present? | |
| 55 | + group.avatar.url | |
| 56 | + else | |
| 57 | + '/assets/no_group_avatar.png' | |
| 58 | + end | |
| 59 | + end | |
| 60 | + | |
| 52 | 61 | def avatar_icon(user_email = '', size = nil) |
| 53 | 62 | user = User.find_by(email: user_email) |
| 54 | 63 | if user && user.avatar.present? | ... | ... |
app/models/group.rb
| ... | ... | @@ -12,10 +12,20 @@ |
| 12 | 12 | # description :string(255) default(""), not null |
| 13 | 13 | # |
| 14 | 14 | |
| 15 | +require 'carrierwave/orm/activerecord' | |
| 16 | +require 'file_size_validator' | |
| 17 | + | |
| 15 | 18 | class Group < Namespace |
| 16 | 19 | has_many :users_groups, dependent: :destroy |
| 17 | 20 | has_many :users, through: :users_groups |
| 18 | 21 | |
| 22 | + attr_accessible :avatar | |
| 23 | + | |
| 24 | + validate :avatar_type, if: ->(user) { user.avatar_changed? } | |
| 25 | + validates :avatar, file_size: { maximum: 100.kilobytes.to_i } | |
| 26 | + | |
| 27 | + mount_uploader :avatar, AttachmentUploader | |
| 28 | + | |
| 19 | 29 | def human_name |
| 20 | 30 | name |
| 21 | 31 | end |
| ... | ... | @@ -50,4 +60,10 @@ class Group < Namespace |
| 50 | 60 | def members |
| 51 | 61 | users_groups |
| 52 | 62 | end |
| 63 | + | |
| 64 | + def avatar_type | |
| 65 | + unless self.avatar.image? | |
| 66 | + self.errors.add :avatar, "only images allowed" | |
| 67 | + end | |
| 68 | + end | |
| 53 | 69 | end | ... | ... |
app/models/namespace.rb
app/views/dashboard/_groups.html.haml
| ... | ... | @@ -10,6 +10,7 @@ |
| 10 | 10 | - groups.each do |group| |
| 11 | 11 | %li.group-row |
| 12 | 12 | = link_to group_path(id: group.path), class: dom_class(group) do |
| 13 | + = image_tag group_icon(group.path), class: "avatar s32" | |
| 13 | 14 | %span.group-name.filter-title |
| 14 | 15 | = truncate(group.name, length: 35) |
| 15 | 16 | %span.arrow | ... | ... |
app/views/groups/edit.html.haml
| ... | ... | @@ -20,7 +20,7 @@ |
| 20 | 20 | %strong= @group.name |
| 21 | 21 | group settings: |
| 22 | 22 | %div.form-holder |
| 23 | - = form_for @group, html: { class: "form-horizontal" } do |f| | |
| 23 | + = form_for @group, html: { multipart: true, class: "form-horizontal" }, authenticity_token: true do |f| | |
| 24 | 24 | - if @group.errors.any? |
| 25 | 25 | .alert.alert-danger |
| 26 | 26 | %span= @group.errors.full_messages.first |
| ... | ... | @@ -35,6 +35,26 @@ |
| 35 | 35 | .col-sm-10 |
| 36 | 36 | = f.text_area :description, maxlength: 250, class: "form-control js-gfm-input", rows: 4 |
| 37 | 37 | |
| 38 | + .form-group | |
| 39 | + .col-sm-2 | |
| 40 | + .col-sm-10 | |
| 41 | + = image_tag group_icon(@group.to_param), alt: '', class: 'avatar s160' | |
| 42 | + %p.light | |
| 43 | + - if @group.avatar? | |
| 44 | + You can change your group avatar here | |
| 45 | + - else | |
| 46 | + You can upload an group avatar here | |
| 47 | + %a.choose-btn.btn.btn-small.js-choose-group-avatar-button | |
| 48 | + %i.icon-paper-clip | |
| 49 | + %span Choose File ... | |
| 50 | + | |
| 51 | + %span.file_name.js-avatar-filename File name... | |
| 52 | + = f.file_field :avatar, class: "js-group-avatar-input hidden" | |
| 53 | + .light The maximum file size allowed is 100KB. | |
| 54 | + - if @group.avatar? | |
| 55 | + %hr | |
| 56 | + = link_to 'Remove avatar', group_avatar_path(@group.to_param), data: { confirm: "Group avatar will be removed. Are you sure?"}, method: :delete, class: "btn btn-remove btn-small remove-avatar" | |
| 57 | + | |
| 38 | 58 | .form-actions |
| 39 | 59 | = f.submit 'Save group', class: "btn btn-save" |
| 40 | 60 | ... | ... |
config/routes.rb
| ... | ... | @@ -156,6 +156,9 @@ Gitlab::Application.routes.draw do |
| 156 | 156 | end |
| 157 | 157 | |
| 158 | 158 | resources :users_groups, only: [:create, :update, :destroy] |
| 159 | + scope module: :groups do | |
| 160 | + resource :avatar, only: [:destroy] | |
| 161 | + end | |
| 159 | 162 | end |
| 160 | 163 | |
| 161 | 164 | resources :projects, constraints: { id: /[^\/]+/ }, only: [:new, :create] | ... | ... |
db/schema.rb
| ... | ... | @@ -11,7 +11,7 @@ |
| 11 | 11 | # |
| 12 | 12 | # It's strongly recommended that you check this file into your version control system. |
| 13 | 13 | |
| 14 | -ActiveRecord::Schema.define(version: 20140122122549) do | |
| 14 | +ActiveRecord::Schema.define(version: 20140127170938) do | |
| 15 | 15 | |
| 16 | 16 | create_table "broadcast_messages", force: true do |t| |
| 17 | 17 | t.text "message", null: false |
| ... | ... | @@ -152,6 +152,7 @@ ActiveRecord::Schema.define(version: 20140122122549) do |
| 152 | 152 | t.datetime "updated_at", null: false |
| 153 | 153 | t.string "type" |
| 154 | 154 | t.string "description", default: "", null: false |
| 155 | + t.string "avatar" | |
| 155 | 156 | end |
| 156 | 157 | |
| 157 | 158 | add_index "namespaces", ["name"], name: "index_namespaces_on_name", using: :btree | ... | ... |
features/group/group.feature
| ... | ... | @@ -31,3 +31,17 @@ Feature: Groups |
| 31 | 31 | And I change group name |
| 32 | 32 | Then I should see new group name |
| 33 | 33 | |
| 34 | + Scenario: I edit my group avatar | |
| 35 | + When I visit group settings page | |
| 36 | + And I change my group avatar | |
| 37 | + And I visit group settings page | |
| 38 | + Then I should see new group avatar | |
| 39 | + And I should see the "Remove avatar" button | |
| 40 | + | |
| 41 | + Scenario: I remove my group avatar | |
| 42 | + When I visit group settings page | |
| 43 | + And I have an group avatar | |
| 44 | + And I visit group settings page | |
| 45 | + And I remove my group avatar | |
| 46 | + Then I should not see my group avatar | |
| 47 | + And I should not see the "Remove avatar" button | ... | ... |
features/steps/group/group.rb
| ... | ... | @@ -98,6 +98,40 @@ class Groups < Spinach::FeatureSteps |
| 98 | 98 | end |
| 99 | 99 | end |
| 100 | 100 | |
| 101 | + step 'I change my group avatar' do | |
| 102 | + attach_file(:group_avatar, File.join(Rails.root, 'public', 'gitlab_logo.png')) | |
| 103 | + click_button "Save group" | |
| 104 | + @group.reload | |
| 105 | + end | |
| 106 | + | |
| 107 | + step 'I should see new group avatar' do | |
| 108 | + @group.avatar.should be_instance_of AttachmentUploader | |
| 109 | + @group.avatar.url.should == "/uploads/group/avatar/#{ @group.id }/gitlab_logo.png" | |
| 110 | + end | |
| 111 | + | |
| 112 | + step 'I should see the "Remove avatar" button' do | |
| 113 | + page.should have_link("Remove avatar") | |
| 114 | + end | |
| 115 | + | |
| 116 | + step 'I have an group avatar' do | |
| 117 | + attach_file(:group_avatar, File.join(Rails.root, 'public', 'gitlab_logo.png')) | |
| 118 | + click_button "Save group" | |
| 119 | + @group.reload | |
| 120 | + end | |
| 121 | + | |
| 122 | + step 'I remove my group avatar' do | |
| 123 | + click_link "Remove avatar" | |
| 124 | + @group.reload | |
| 125 | + end | |
| 126 | + | |
| 127 | + step 'I should not see my group avatar' do | |
| 128 | + @group.avatar?.should be_false | |
| 129 | + end | |
| 130 | + | |
| 131 | + step 'I should not see the "Remove avatar" button' do | |
| 132 | + page.should_not have_link("Remove avatar") | |
| 133 | + end | |
| 134 | + | |
| 101 | 135 | protected |
| 102 | 136 | |
| 103 | 137 | def current_group | ... | ... |
spec/helpers/application_helper_spec.rb
| ... | ... | @@ -39,6 +39,23 @@ describe ApplicationHelper do |
| 39 | 39 | end |
| 40 | 40 | end |
| 41 | 41 | |
| 42 | + describe "group_icon" do | |
| 43 | + avatar_file_path = File.join(Rails.root, 'public', 'gitlab_logo.png') | |
| 44 | + | |
| 45 | + it "should return an url for the avatar" do | |
| 46 | + group = create(:group) | |
| 47 | + group.avatar = File.open(avatar_file_path) | |
| 48 | + group.save! | |
| 49 | + group_icon(group.path).to_s.should == "/uploads/group/avatar/#{ group.id }/gitlab_logo.png" | |
| 50 | + end | |
| 51 | + | |
| 52 | + it "should give default avatar_icon when no avatar is present" do | |
| 53 | + group = create(:group) | |
| 54 | + group.save! | |
| 55 | + group_icon(group.path).to_s.should == "/assets/no_group_avatar.png" | |
| 56 | + end | |
| 57 | + end | |
| 58 | + | |
| 42 | 59 | describe "avatar_icon" do |
| 43 | 60 | avatar_file_path = File.join(Rails.root, 'public', 'gitlab_logo.png') |
| 44 | 61 | ... | ... |
spec/models/group_spec.rb
| ... | ... | @@ -54,4 +54,19 @@ describe Group do |
| 54 | 54 | group.users_groups.guests.map(&:user).should_not include(user) |
| 55 | 55 | end |
| 56 | 56 | end |
| 57 | + | |
| 58 | + describe :avatar_type do | |
| 59 | + let(:user) { create(:user) } | |
| 60 | + before { group.add_user(user, UsersGroup::MASTER) } | |
| 61 | + | |
| 62 | + it "should be true if avatar is image" do | |
| 63 | + group.update_attribute(:avatar, 'uploads/avatar.png') | |
| 64 | + group.avatar_type.should be_true | |
| 65 | + end | |
| 66 | + | |
| 67 | + it "should be false if avatar is html page" do | |
| 68 | + group.update_attribute(:avatar, 'uploads/avatar.html') | |
| 69 | + group.avatar_type.should == ["only images allowed"] | |
| 70 | + end | |
| 71 | + end | |
| 57 | 72 | end | ... | ... |