From 17a801394e79f23fdd658e094770e24f96c24a96 Mon Sep 17 00:00:00 2001
From: maxwell <maxwell@joindiaspora.com>
Date: Tue, 15 Feb 2011 17:12:49 -0800
Subject: [PATCH] work in progress. need to update the views for the controller
 changes

---
 '                                             | 43 +++++++++++
 .../aspect_memberships_controller.rb          | 50 +++++++++++++
 app/controllers/aspects_controller.rb         | 29 --------
 app/controllers/contacts_controller.rb        | 11 +++
 app/models/aspect_membership.rb               | 11 +++
 app/models/user.rb                            | 12 ----
 config/locales/diaspora/en.yml                | 11 +--
 config/routes.rb                              |  3 +
 lib/diaspora/user/querying.rb                 |  1 +
 .../aspect_memberships_controller_spec.rb     | 72 +++++++++++++++++++
 spec/controllers/aspects_controller_spec.rb   | 13 ----
 spec/controllers/contacts_controller_spec.rb  | 24 +++++++
 spec/models/aspect_membership_spec.rb         | 34 +++++++++
 spec/models/user/querying_spec.rb             |  4 ++
 14 files changed, 260 insertions(+), 58 deletions(-)
 create mode 100644 '
 create mode 100644 app/controllers/aspect_memberships_controller.rb
 create mode 100644 app/controllers/contacts_controller.rb
 create mode 100644 spec/controllers/aspect_memberships_controller_spec.rb
 create mode 100644 spec/controllers/contacts_controller_spec.rb
 create mode 100644 spec/models/aspect_membership_spec.rb

diff --git a/' b/'
new file mode 100644
index 0000000000..95265a85e8
--- /dev/null
+++ b/'
@@ -0,0 +1,43 @@
+#   Copyright (c) 2010, Diaspora Inc.  This file is
+#   licensed under the Affero General Public License version 3 or later.  See
+#   the COPYRIGHT file.
+
+require 'spec_helper'
+
+describe AspectMembershipsController do
+  before do
+    @user  = alice
+    @user2 = bob
+
+    @aspect0  = @user.aspects.first
+    @aspect1  = @user.aspects.create(:name => "another aspect")
+    @aspect2  = @user2.aspects.first
+
+    @contact = @user.contact_for(@user2.person)
+    @user.getting_started = false
+    @user.save
+    sign_in :user, @user
+    @controller.stub(:current_user).and_return(@user)
+    request.env["HTTP_REFERER"] = 'http://' + request.host
+  end
+
+  describe "#new" do
+    it 'succeeds' do
+      get :new
+      response.should be_success
+    end
+  end
+
+  describe "#destroy" do
+    it 'removes contacts from an aspect' do
+      @user.add_contact_to_aspect(@contact, @aspect1)
+      delete :destroy,
+        :format => 'js', :id => 123,
+        :person_id => @user2.person.id,
+        :aspect_id => @aspect0.id
+      response.should be_success
+      @aspect0.reload
+      @aspect0.contacts.include?(@contact).should be false
+    end
+  end
+end
diff --git a/app/controllers/aspect_memberships_controller.rb b/app/controllers/aspect_memberships_controller.rb
new file mode 100644
index 0000000000..28bdaea19d
--- /dev/null
+++ b/app/controllers/aspect_memberships_controller.rb
@@ -0,0 +1,50 @@
+#   Copyright (c) 2010, Diaspora Inc.  This file is
+#   licensed under the Affero General Public License version 3 or later.  See
+#   the COPYRIGHT file.
+#
+
+class AspectMembershipsController < ApplicationController 
+  before_filter :authenticate_user!
+
+  def new
+    render :nothing => true
+  end
+
+ 
+  def destroy 
+    #note :id is garbage
+
+
+      @person_id = params[:person_id]
+      @aspect_id = params[:aspect_id]
+
+      contact = current_user.contact_for(Person.where(:id => @person_id).first)
+
+      membership = contact ? contact.aspect_memberships.where(:aspect_id => @aspect_id).first : nil
+
+      if membership && membership.destroy
+        flash.now[:notice] = I18n.t 'aspect_memberships.destroy.success'
+
+        respond_to do |format|
+          format.js { render :json => {:button_html =>
+            render_to_string(:partial => 'aspects/remove_from_aspect',
+                             :locals => {:aspect_id => @aspect_id,
+                               :person_id => @person_id}),
+                               :aspect_id => @aspect_id
+          }}
+          format.html{
+            redirect_to :back
+          }
+        end
+      else
+        flash.now[:error] = I18n.t 'aspect_memberships.destroy.failure'
+        errors = membership ? membership.errors.full_messages : t('aspect_memberships.destroy.no_membership')
+        respond_to do |format|
+          format.js  { render :text => errors, :status => 403 }
+          format.html{
+            redirect_to :back
+          }
+      end
+    end
+  end
+end
diff --git a/app/controllers/aspects_controller.rb b/app/controllers/aspects_controller.rb
index f6d0493180..e577c44b1a 100644
--- a/app/controllers/aspects_controller.rb
+++ b/app/controllers/aspects_controller.rb
@@ -177,35 +177,6 @@ class AspectsController < ApplicationController
     end
   end
 
-  def remove_from_aspect
-    begin current_user.delete_person_from_aspect(params[:person_id], params[:aspect_id])
-      @person_id = params[:person_id]
-      @aspect_id = params[:aspect_id]
-      flash.now[:notice] = I18n.t 'aspects.remove_from_aspect.success'
-
-      respond_to do |format|
-        format.js { render :json => {:button_html =>
-          render_to_string(:partial => 'aspects/remove_from_aspect',
-                           :locals => {:aspect_id => @aspect_id,
-                                       :person_id => @person_id}),
-          :aspect_id => @aspect_id
-        }}
-        format.html{
-          redirect_to :back
-        }
-      end
-    rescue Exception => e
-      flash.now[:error] = I18n.t 'aspects.remove_from_aspect.failure'
-
-      respond_to do |format|
-        format.js  { render :text => e, :status => 403 }
-        format.html{
-          redirect_to :back
-        }
-      end
-    end
-  end
-
   private
   def invite_or_add_contact_to_aspect( aspect, person, contact)
     if contact
diff --git a/app/controllers/contacts_controller.rb b/app/controllers/contacts_controller.rb
new file mode 100644
index 0000000000..f32fa8ae7a
--- /dev/null
+++ b/app/controllers/contacts_controller.rb
@@ -0,0 +1,11 @@
+#   Copyright (c) 2010, Diaspora Inc.  This file is
+#   licensed under the Affero General Public License version 3 or later.  See
+#   the COPYRIGHT file.
+
+class ContactsController < ApplicationController
+  before_filter :authenticate_user!
+  
+  def new
+    render :nothing => true
+  end
+end
diff --git a/app/models/aspect_membership.rb b/app/models/aspect_membership.rb
index f79d315206..2b8cb4c414 100644
--- a/app/models/aspect_membership.rb
+++ b/app/models/aspect_membership.rb
@@ -9,4 +9,15 @@ class AspectMembership < ActiveRecord::Base
   has_one :user, :through => :contact
   has_one :person, :through => :contact
 
+  before_destroy :ensure_membership
+  
+  
+  def ensure_membership
+    if self.contact.aspect_memberships.count == 1
+      errors[:base] << I18n.t('shared.contact_list.cannot_remove')
+      false
+    else
+      true
+    end
+  end
 end
diff --git a/app/models/user.rb b/app/models/user.rb
index 450d9ab7f1..fa4ec5e522 100644
--- a/app/models/user.rb
+++ b/app/models/user.rb
@@ -92,18 +92,6 @@ class User < ActiveRecord::Base
     contact.aspect_memberships.create!(:aspect => aspect)
   end
 
-  def delete_person_from_aspect(person_id, aspect_id, opts = {})
-    aspect = Aspect.find(aspect_id)
-    raise "Can not delete a person from an aspect you do not own" unless aspect.user == self
-    contact = contact_for Person.find(person_id)
-
-    if opts[:force] || contact.aspect_ids.count > 1
-      contact.aspects.delete(aspect)
-    else
-      raise "Can not delete a person from last aspect"
-    end
-  end
-
   ######## Posting ########
   def build_post(class_name, opts = {})
     opts[:person] = self.person
diff --git a/config/locales/diaspora/en.yml b/config/locales/diaspora/en.yml
index 5b284a9b32..5063a6ec2f 100644
--- a/config/locales/diaspora/en.yml
+++ b/config/locales/diaspora/en.yml
@@ -142,6 +142,12 @@ en:
       contact_list:
           all_contacts: "All contacts"
           cannot_remove: "Cannot remove person from last aspect. (If you want to disconnect from this person you must remove contact.)"
+  aspect_memberships:
+      destroy:
+          success: "Successfully removed person from aspect"
+          failure: "Failed to remove person from aspect"
+          no_membership: "Could not find the selected person in that aspect"
+ 
   aspects:
       contacts_visible: "Contacts in this aspect will be able to see each other."
       contacts_not_visible: "Contacts in this aspect will not be able to see each other."
@@ -194,9 +200,6 @@ en:
           remove: "remove"
           aspect_not_empty: "Aspect not empty"
           are_you_sure: "Are you sure you want to delete this aspect?"
-      remove_from_aspect:
-          success: "Successfully removed person from aspect"
-          failure: "Failed to remove person from aspect"
       seed:
           family: "Family"
           work: "Work"
@@ -404,7 +407,7 @@ en:
       aspect_list:
            edit_membership: "edit aspect membership"
       share_with_pane:
-           add_new_aspect: "add new aspect"
+           add_new_aspect: "add to new aspect"
   requests:
       manage_aspect_contacts:
           manage_within: "Manage contacts within"
diff --git a/config/routes.rb b/config/routes.rb
index 9fff5dd9d2..11663df92d 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -21,6 +21,9 @@ Diaspora::Application.routes.draw do
   resources :notifications,   :only => [:index, :update]
   resources :posts,           :only => [:show], :path => '/p/'
 
+  resources :contacts
+  resources :aspect_memberships
+
   match '/people/share_with' => 'people#share_with', :as => 'share_with'
   resources :people, :except => [:edit, :update] do
     resources :status_messages
diff --git a/lib/diaspora/user/querying.rb b/lib/diaspora/user/querying.rb
index 7b2fe0a617..173c334e6d 100644
--- a/lib/diaspora/user/querying.rb
+++ b/lib/diaspora/user/querying.rb
@@ -34,6 +34,7 @@ module Diaspora
       end
 
       def contact_for(person)
+        return nil unless person
         contact_for_person_id(person.id)
       end
       def aspects_with_post(post_id)
diff --git a/spec/controllers/aspect_memberships_controller_spec.rb b/spec/controllers/aspect_memberships_controller_spec.rb
new file mode 100644
index 0000000000..11fd0c1ec1
--- /dev/null
+++ b/spec/controllers/aspect_memberships_controller_spec.rb
@@ -0,0 +1,72 @@
+#   Copyright (c) 2010, Diaspora Inc.  This file is
+#   licensed under the Affero General Public License version 3 or later.  See
+#   the COPYRIGHT file.
+
+require 'spec_helper'
+
+describe AspectMembershipsController do
+  before do
+    @user  = alice
+    @user2 = bob
+
+    @aspect0  = @user.aspects.first
+    @aspect1  = @user.aspects.create(:name => "another aspect")
+    @aspect2  = @user2.aspects.first
+
+    @contact = @user.contact_for(@user2.person)
+    @user.getting_started = false
+    @user.save
+    sign_in :user, @user
+    @controller.stub(:current_user).and_return(@user)
+    request.env["HTTP_REFERER"] = 'http://' + request.host
+  end
+
+  describe "#new" do
+    it 'succeeds' do
+      get :new
+      response.should be_success
+    end
+  end
+
+  describe "#destroy" do
+    it 'removes contacts from an aspect' do
+      @user.add_contact_to_aspect(@contact, @aspect1)
+      delete :destroy,
+        :format => 'js', :id => 123,
+        :person_id => @user2.person.id,
+        :aspect_id => @aspect0.id
+      response.should be_success
+      @aspect0.reload
+      @aspect0.contacts.include?(@contact).should be false
+    end
+
+    context 'aspect membership does not exist' do
+      it 'person does not exist' do
+        delete :destroy,
+          :format => 'js', :id => 123,
+          :person_id => 4324525,
+          :aspect_id => @aspect0.id
+        response.should_not be_success
+        response.body.should include "Could not find the selected person in that aspect"
+      end
+
+      it 'contact is not in the aspect' do
+        delete :destroy,
+          :format => 'js', :id => 123,
+          :person_id => @user2.person.id,
+          :aspect_id => 2321
+        response.should_not be_success
+        response.body.should include "Could not find the selected person in that aspect"
+      end
+    end
+
+    it 'has the error of cannot delete contact from last aspect if its the last aspect' do
+      delete :destroy,
+        :format => 'js', :id => 123,
+        :person_id => @user2.person.id,
+        :aspect_id => @aspect0.id
+      response.should_not be_success
+      response.body.should include "Cannot remove person from last aspect"
+    end
+  end
+end
diff --git a/spec/controllers/aspects_controller_spec.rb b/spec/controllers/aspects_controller_spec.rb
index b2e29c5a73..bb59a33731 100644
--- a/spec/controllers/aspects_controller_spec.rb
+++ b/spec/controllers/aspects_controller_spec.rb
@@ -319,19 +319,6 @@ describe AspectsController do
     end
   end
 
-  describe "#remove_from_aspect" do
-    it 'removes contacts from an aspect' do
-      @user.add_contact_to_aspect(@contact, @aspect1)
-      post 'remove_from_aspect',
-        :format => 'js',
-        :person_id => @user2.person.id,
-        :aspect_id => @aspect0.id
-      response.should be_success
-      @aspect0.reload
-      @aspect0.contacts.include?(@contact).should be false
-    end
-  end
-
   describe "#hashes_for_posts" do
     it 'returns only distinct people' do
     end
diff --git a/spec/controllers/contacts_controller_spec.rb b/spec/controllers/contacts_controller_spec.rb
new file mode 100644
index 0000000000..8ba4c86d81
--- /dev/null
+++ b/spec/controllers/contacts_controller_spec.rb
@@ -0,0 +1,24 @@
+#   Copyright (c) 2010, Diaspora Inc.  This file is
+#   licensed under the Affero General Public License version 3 or later.  See
+#   the COPYRIGHT file.
+
+
+require 'spec_helper'
+
+describe ContactsController do
+  render_views
+
+  before do
+    @user = alice
+    sign_in :user, @user
+  end
+
+  describe 'new' do
+
+    it 'succeeds' do
+      pending "This is going to be new request"
+      get :new
+      response.should be_success
+    end
+  end
+end
diff --git a/spec/models/aspect_membership_spec.rb b/spec/models/aspect_membership_spec.rb
new file mode 100644
index 0000000000..efb6be8807
--- /dev/null
+++ b/spec/models/aspect_membership_spec.rb
@@ -0,0 +1,34 @@
+#   Copyright (c) 2010, Diaspora Inc.  This file is
+#   licensed under the Affero General Public License version 3 or later.  See
+#   the COPYRIGHT file.
+#
+require 'spec_helper'
+
+describe AspectMembership do
+  before do
+    @user = alice
+    @user2 = bob
+    @aspect = @user.aspects.create(:name => 'Boozers')
+    @contact = @user.contact_for(@user2.person)
+  end
+
+  it 'has an aspect' do
+    am = AspectMembership.new(:aspect => @aspect)
+    am.aspect.should == @aspect
+  end
+
+  it 'has a contact' do
+    am = AspectMembership.new(:contact => @contact)
+    am.contact.should == @contact 
+  end
+
+  context 'validations' do
+    describe '#ensure_membership' do
+      it 'does not destroy from the final aspect' do
+        am = @contact.aspect_memberships.first
+        am.destroy
+        am.errors.should_not be_empty
+      end
+    end
+  end
+end
diff --git a/spec/models/user/querying_spec.rb b/spec/models/user/querying_spec.rb
index 0b7ba0ef7c..da876409c0 100644
--- a/spec/models/user/querying_spec.rb
+++ b/spec/models/user/querying_spec.rb
@@ -193,6 +193,10 @@ describe User do
         @user.should_receive(:contact_for_person_id).with(person_one.id)
         @user.contact_for(person_one)
       end
+
+      it 'returns nil if the input is nil' do
+        @user.contact_for(nil).should be_nil 
+      end
     end
   end
 
-- 
GitLab