[rspec-users] First encounter with RSpec, please help

Jesse Crockett lists at ruby-forum.com
Sun Aug 10 19:22:29 EDT 2008


Connection

# == Schema Information
# Schema version: 26
#
# Table name: connections
#
#  id          :integer(11)     not null, primary key
#  person_id   :integer(11)
#  contact_id  :integer(11)
#  status      :integer(11)
#  accepted_at :datetime
#  created_at  :datetime
#  updated_at  :datetime
#

class Connection < ActiveRecord::Base
  extend ActivityLogger
  extend PreferencesHelper

  belongs_to :person
  belongs_to :contact, :class_name => "Person", :foreign_key => 
"contact_id"
  has_many :activities, :foreign_key => "item_id", :dependent => 
:destroy
  validates_presence_of :person_id, :contact_id

  # Status codes.
  ACCEPTED  = 0
  REQUESTED = 1
  PENDING   = 2

  # Accept a connection request (instance method).
  # Each connection is really two rows, so delegate this method
  # to Connection.accept to wrap the whole thing in a transaction.
  def accept
    Connection.accept(person_id, contact_id)
  end

  def breakup
    Connection.breakup(person_id, contact_id)
  end

  class << self

    # Return true if the persons are (possibly pending) connections.
    def exists?(person, contact)
      not conn(person, contact).nil?
    end

    alias exist? exists?

    # Make a pending connection request.
    def request(person, contact, send_mail = nil)
      if send_mail.nil?
        send_mail = global_prefs.email_notifications? &&
                    contact.connection_notifications?
      end
      if person == contact or Connection.exists?(person, contact)
        nil
      else
        transaction do
          create(:person => person, :contact => contact, :status => 
PENDING)
          create(:person => contact, :contact => person, :status => 
REQUESTED)
        end
        if send_mail
          # The order here is important: the mail is sent *to* the 
contact,
          # so the connection should be from the contact's point of 
view.
          connection = conn(contact, person)
          PersonMailer.deliver_connection_request(connection)
        end
        true
      end
    end

    # Accept a connection request.
    def accept(person, contact)
      transaction do
        accepted_at = Time.now
        accept_one_side(person, contact, accepted_at)
        accept_one_side(contact, person, accepted_at)
      end
      log_activity(conn(person, contact))
    end

    def connect(person, contact, send_mail = nil)
      transaction do
        request(person, contact, send_mail)
        accept(person, contact)
      end
      conn(person, contact)
    end

    # Delete a connection or cancel a pending request.
    def breakup(person, contact)
      transaction do
        destroy(conn(person, contact))
        destroy(conn(contact, person))
      end
    end

    # Return a connection based on the person and contact.
    def conn(person, contact)
      find_by_person_id_and_contact_id(person, contact)
    end

    def accepted?(person, contact)
      conn(person, contact).status == ACCEPTED
    end

    def connected?(person, contact)
      exist?(person, contact) and accepted?(person, contact)
    end
  end

  private

  class << self
    # Update the db with one side of an accepted connection request.
    def accept_one_side(person, contact, accepted_at)
      conn = conn(person, contact)
      conn.update_attributes!(:status => ACCEPTED,
                              :accepted_at => accepted_at)
    end

    def log_activity(conn)
      activity = Activity.create!(:item => conn, :person => conn.person)
      add_activities(:activity => activity, :person => conn.person)
      add_activities(:activity => activity, :person => conn.contact)
    end
  end
end

Controller

class ConnectionsController < ApplicationController

  before_filter :login_required, :setup
  before_filter :authorize_view, :only => :index
  before_filter :authorize_person, :only => [:edit, :update, :destroy]
  before_filter :redirect_for_inactive, :only => [:edit, :update]

  # Show all the contacts for a person.
  def index
    @contacts = @person.contacts.paginate(:page => params[:page],
                                          :per_page => RASTER_PER_PAGE)
  end

  def edit
    @contact = @connection.contact
  end

  def create
    @contact = Person.find(params[:person_id])

    respond_to do |format|
      if can_request? and Connection.request(current_person, @contact)
        flash[:notice] = 'Connection request sent!'
        format.html { redirect_to(home_url) }
      else
        # This should only happen when people exceed daily request limit
        # or something funky like friending themselves.
        flash[:notice] = "Invalid connection or exceeds daily \
              request limit 
(#{Preference.find(:first).daily_request_limit})."
        format.html { redirect_to(home_url) }
      end
    end
  end

  # validate against admin daily connection request limit
  def can_request?
    @requests_limited = Preference.find(:first).limit_requests
    @limit = Preference.find(:first).daily_request_limit
    if @requests_limited
      @list = 
Connection.find_all_by_person_id_and_status(current_person,
                          Connection::PENDING, :order => 'created_at 
desc')
      if @limit == 0
        false
      elsif not @list[@limit - 1].nil?
        @list[@limit - 1].created_at < 1.day.ago
      else
        true
      end
    end
  end

  def update

    respond_to do |format|
      contact = @connection.contact
      name = contact.name
      case params[:commit]
      when "Accept"
        @connection.accept
        flash[:notice] = %(Accepted connection with
                           <a href="#{person_url(contact)}">#{name}</a>)
      when "Decline"
        @connection.breakup
        flash[:notice] = "Declined connection with #{name}"
      end
      format.html { redirect_to(home_url) }
    end
  end

  def destroy
    @connection.breakup

    respond_to do |format|
      flash[:success] = "Ended connection with 
#{@connection.contact.name}"
      format.html { redirect_to( person_connections_url(current_person)) 
}
    end
  end

  private

    def setup
      # Connections have same body class as profiles.
      @body = "profile"
    end

    def authorize_view
      @person = Person.find(params[:person_id])
      unless (current_person?(@person) or
              Connection.connected?(@person, current_person))
        redirect_to home_url
      end
    end

    # Make sure the current person is correct for this connection.
    def authorize_person
      @connection = Connection.find(params[:id],
                                    :include => [:person, :contact])
      unless current_person?(@connection.person)
        flash[:error] = "Invalid connection."
        redirect_to home_url
      end
    rescue ActiveRecord::RecordNotFound
      flash[:error] = "Invalid or expired connection request"
      redirect_to home_url
    end

    # Redirect if the target person is inactive.
    # Suppose Alice sends Bob a connection request, but then the admin
    # deactivates Alice.  We don't want Bob to be able to make the 
connection.
    def redirect_for_inactive
      if @connection.contact.deactivated?
        flash[:error] = "Invalid connection request: person deactivated"
        redirect_to home_url
      end
    end

end

Error

1)
Spec::Mocks::MockExpectationError in 'ConnectionsController should 
create a new connection request'
Mock 'Class' expected :request with (I'm Quentin, I'm Aaron) once, but 
received it 0 times
./spec/controllers/connections_controller_spec.rb:18:

Finished in 10.707133 seconds


David Chelimsky wrote:
> On Sun, Aug 10, 2008 at 11:03 AM, Jesse Crockett <lists at ruby-forum.com> 
> wrote:
>> require File.dirname(__FILE__) + '/../spec_helper'
>>  end
>>
>>    @contact = people(:aaron)
>>      and_return(true)
>>    post :create, :person_id => @contact
>>    response.should redirect_to(home_url)
>>  end
>>
>> # abridged
>>
>> The two vars needed can be accessed in the connection_spec with
>> @global_prefs.limit_requests and @global_prefs.daily_request_limit
>>
>> Please help me clear this problem.
> 
> Please post the code for Connection and Controller as well.

-- 
Posted via http://www.ruby-forum.com/.


More information about the rspec-users mailing list