From 0b4d7363524f706e00185a29ae04ffbe23d618a7 Mon Sep 17 00:00:00 2001 From: Diego Araújo Date: Fri, 24 Jan 2014 12:59:27 -0200 Subject: [PATCH] Ownerships and Controller for Configuration. --- app/controllers/concerns/ownership_authentication.rb | 4 ++-- app/controllers/mezuro_configurations_controller.rb | 88 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-------------------- app/models/mezuro_configuration.rb | 6 +++++- app/models/mezuro_configuration_ownership.rb | 8 ++++++++ app/models/user.rb | 6 ++++++ db/migrate/20140124124835_create_mezuro_configuration_ownerships.rb | 10 ++++++++++ spec/controllers/mezuro_configurations_controller_spec.rb | 270 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ spec/factories/mezuro_configuration_ownerships.rb | 2 +- spec/models/mezuro_configuration_ownership_spec.rb | 22 ++++++++++++++++++++++ spec/models/mezuro_configuration_spec.rb | 11 +++++++++++ spec/models/user_spec.rb | 16 ++++++++++++++++ 11 files changed, 419 insertions(+), 24 deletions(-) create mode 100644 app/models/mezuro_configuration_ownership.rb create mode 100644 db/migrate/20140124124835_create_mezuro_configuration_ownerships.rb create mode 100644 spec/controllers/mezuro_configurations_controller_spec.rb create mode 100644 spec/models/mezuro_configuration_ownership_spec.rb diff --git a/app/controllers/concerns/ownership_authentication.rb b/app/controllers/concerns/ownership_authentication.rb index 2ff75f2..7ff3dd8 100644 --- a/app/controllers/concerns/ownership_authentication.rb +++ b/app/controllers/concerns/ownership_authentication.rb @@ -26,7 +26,7 @@ module OwnershipAuthentication end def mezuro_configuration_owner? - check_mezuro_configuration_ownership(params[:configuration_id]) + check_mezuro_configuration_ownership(params[:id]) end private @@ -52,7 +52,7 @@ module OwnershipAuthentication def check_mezuro_configuration_ownership(id) if current_user.mezuro_configuration_ownerships.find_by_mezuro_configuration_id(id).nil? respond_to do |format| - format.html { redirect_to mezuro_configuration_url(id), notice: "You're not allowed to do this operation" } + format.html { redirect_to mezuro_configurations_url, notice: "You're not allowed to do this operation" } format.json { head :no_content } end end diff --git a/app/controllers/mezuro_configurations_controller.rb b/app/controllers/mezuro_configurations_controller.rb index e1b8da5..595d317 100644 --- a/app/controllers/mezuro_configurations_controller.rb +++ b/app/controllers/mezuro_configurations_controller.rb @@ -1,38 +1,86 @@ +include OwnershipAuthentication + class MezuroConfigurationsController < ApplicationController + before_action :authenticate_user!, + except: [:index, :show] + before_action :mezuro_configuration_owner?, only: [:edit, :update, :destroy] + # GET /mezuro_configurations/new + def new + @mezuro_configuration = MezuroConfiguration.new + end + + # GET /mezuro_configurations + # GET /mezuro_configurations.json def index - @configurations = MezuroConfiguration.all + @mezuro_configurations = MezuroConfiguration.all end - + + # POST /mezuro_configurations + # POST /mezuro_configurations.json + def create + @mezuro_configuration = MezuroConfiguration.new(mezuro_configuration_params) + respond_to do |format| + create_and_redir(format) + end + end + + # GET /mezuro_configurations/1 + # GET /mezuro_configurations/1.json def show - @configuration = MezuroConfiguration.find(params[:id]) + set_mezuro_configuration + @mezuro_configuration_metric_configurations = @mezuro_configuration.metric_configurations end - def new - @configuration = MezuroConfiguration.new + # GET /mezuro_configurations/1/edit + # GET /mezuro_configurations/1/edit.json + def edit + set_mezuro_configuration end - def create - @configuration = MezuroConfiguration.new(configuration_params) - if @configuration.save - redirect_to mezuro_configuration_path(@configuration.id), - notice: 'Configuração criada com sucesso!' - else - render action: :new - end + + def update + set_mezuro_configuration + if @mezuro_configuration.update(mezuro_configuration_params) + redirect_to(mezuro_configuration_path(@mezuro_configuration.id)) + else + render "edit" + end end - def edit - @configuration = MezuroConfiguration.find(params[:id]) + # DELETE /mezuro_configurations/1 + # DELETE /mezuro_configurations/1.json + def destroy + set_mezuro_configuration + current_user.mezuro_configuration_ownerships.find_by_mezuro_configuration_id(@mezuro_configuration.id).destroy + @mezuro_configuration.destroy + respond_to do |format| + format.html { redirect_to mezuro_configurations_url } + format.json { head :no_content } + end end private + # Use callbacks to share common setup or constraints between actions. + def set_mezuro_configuration + @mezuro_configuration = MezuroConfiguration.find(params[:id]) + end - def configuration_params - params. - require(:mezuro_configuration). - permit(:name, :description) + # Never trust parameters from the scary internet, only allow the white list through. + def mezuro_configuration_params + params[:mezuro_configuration] end -end + # Extracted code from create action + def create_and_redir(format) + if @mezuro_configuration.save + current_user.mezuro_configuration_ownerships.create mezuro_configuration_id: @mezuro_configuration.id + format.html { redirect_to mezuro_configuration_path(@mezuro_configuration.id), notice: 'mezuro_configuration was successfully created.' } + format.json { render action: 'show', status: :created, location: @mezuro_configuration } + else + format.html { render action: 'new' } + format.json { render json: @mezuro_configuration.errors, status: :unprocessable_entity } + end + end +end diff --git a/app/models/mezuro_configuration.rb b/app/models/mezuro_configuration.rb index de186d4..b3e58d3 100644 --- a/app/models/mezuro_configuration.rb +++ b/app/models/mezuro_configuration.rb @@ -5,4 +5,8 @@ class MezuroConfiguration < KalibroGem::Entities::Configuration attr_accessor :name validates :name, presence: true, kalibro_uniqueness: true -end \ No newline at end of file + + def metric_configurations + KalibroGem::Entities::MetricConfiguration.metric_configurations_of(self.id) + end +end diff --git a/app/models/mezuro_configuration_ownership.rb b/app/models/mezuro_configuration_ownership.rb new file mode 100644 index 0000000..8025e1d --- /dev/null +++ b/app/models/mezuro_configuration_ownership.rb @@ -0,0 +1,8 @@ +class MezuroConfigurationOwnership < ActiveRecord::Base + belongs_to :user + validates :mezuro_configuration_id, presence: true + + def mezuro_configuration + MezuroConfiguration.find(mezuro_configuration_id) + end +end diff --git a/app/models/user.rb b/app/models/user.rb index c2ce50e..bfbbc0d 100644 --- a/app/models/user.rb +++ b/app/models/user.rb @@ -11,6 +11,8 @@ class User < ActiveRecord::Base has_many :project_ownerships has_many :reading_group_ownerships + + has_many :mezuro_configuration_ownerships # Alert: when adding new parameters to this model, they should also be added to registrations_controller def projects @@ -20,4 +22,8 @@ class User < ActiveRecord::Base def reading_groups reading_group_ownerships.map { |reading_group_ownership| reading_group_ownership.reading_group } end + + def mezuro_configurations + mezuro_configuration_ownerships.map { |mezuro_configuration_ownership| mezuro_configuration_ownership.mezuro_configuration } + end end diff --git a/db/migrate/20140124124835_create_mezuro_configuration_ownerships.rb b/db/migrate/20140124124835_create_mezuro_configuration_ownerships.rb new file mode 100644 index 0000000..7dec5a5 --- /dev/null +++ b/db/migrate/20140124124835_create_mezuro_configuration_ownerships.rb @@ -0,0 +1,10 @@ +class CreateMezuroConfigurationOwnerships < ActiveRecord::Migration + def change + create_table :mezuro_configuration_ownerships do |t| + t.integer :user_id + t.integer :mezuro_configuration_id + + t.timestamps + end + end +end diff --git a/spec/controllers/mezuro_configurations_controller_spec.rb b/spec/controllers/mezuro_configurations_controller_spec.rb new file mode 100644 index 0000000..cdca0e6 --- /dev/null +++ b/spec/controllers/mezuro_configurations_controller_spec.rb @@ -0,0 +1,270 @@ +require 'spec_helper' + +describe MezuroConfigurationsController do + + describe 'new' do + before :each do + sign_in FactoryGirl.create(:user) + get :new + end + + it { should respond_with(:success) } + it { should render_template(:new) } + end + + describe 'create' do + before do + sign_in FactoryGirl.create(:user) + end + + context 'with valid fields' do + let(:mezuro_configuration) { FactoryGirl.build(:mezuro_configuration) } + let(:subject_params) { Hash[FactoryGirl.attributes_for(:mezuro_configuration).map { |k,v| [k.to_s, v.to_s] }] } #FIXME: Mocha is creating the expectations with strings, but FactoryGirl returns everything with sybols and integers + + before :each do + MezuroConfiguration.any_instance.expects(:save).returns(true) + end + + context 'rendering the show' do + before :each do + MezuroConfiguration.expects(:exists?).returns(true) + + post :create, :mezuro_configuration => subject_params + end + + it 'should redirect to the show view' do + response.should redirect_to mezuro_configuration_path(mezuro_configuration) + end + end + + context 'without rendering the show view' do + before :each do + post :create, :mezuro_configuration => subject_params + end + + it { should respond_with(:redirect) } + end + end + + context 'with an invalid field' do + before :each do + @subject = FactoryGirl.build(:mezuro_configuration) + @subject_params = Hash[FactoryGirl.attributes_for(:mezuro_configuration).map { |k,v| [k.to_s, v.to_s] }] #FIXME: Mocha is creating the expectations with strings, but FactoryGirl returns everything with sybols and integers + + MezuroConfiguration.expects(:new).at_least_once.with(@subject_params).returns(@subject) + MezuroConfiguration.any_instance.expects(:save).returns(false) + + post :create, :mezuro_configuration => @subject_params + end + + it { should render_template(:new) } + end + end + + describe 'show' do + subject { FactoryGirl.build(:mezuro_configuration) } + let(:metric_configuration) { FactoryGirl.build(:metric_configuration) } + before :each do + MezuroConfiguration.expects(:find).with(subject.id.to_s).returns(subject) + subject.expects(:metric_configurations).returns(metric_configuration) + get :show, :id => subject.id + end + + it { should render_template(:show) } + end + + describe 'destroy' do + before do + @subject = FactoryGirl.build(:mezuro_configuration) + end + + context 'with an User logged in' do + before do + sign_in FactoryGirl.create(:user) + @ownership = FactoryGirl.build(:mezuro_configuration_ownership) + @ownerships = [] + end + + context 'when the user owns the mezuro_configuration' do + before :each do + @ownership.expects(:destroy) + @subject.expects(:destroy) + + #Those two mocks looks the same but they are necessary since params[:id] is a String and @mezuro_configuration.id is an Integer :( + @ownerships.expects(:find_by_mezuro_configuration_id).with("#{@subject.id}").returns(@ownership) + @ownerships.expects(:find_by_mezuro_configuration_id).with(@subject.id).returns(@ownership) + + User.any_instance.expects(:mezuro_configuration_ownerships).at_least_once.returns(@ownerships) + + MezuroConfiguration.expects(:find).with(@subject.id.to_s).returns(@subject) + delete :destroy, :id => @subject.id + end + + it 'should redirect to the mezuro_configurations page' do + response.should redirect_to mezuro_configurations_url + end + + it { should respond_with(:redirect) } + end + + context "when the user doesn't own the mezuro_configuration" do + before :each do + @ownerships.expects(:find_by_mezuro_configuration_id).with("#{@subject.id}").returns(nil) + User.any_instance.expects(:mezuro_configuration_ownerships).at_least_once.returns(@ownerships) + + delete :destroy, :id => @subject.id + end + + it { should redirect_to(mezuro_configurations_path) } + end + end + + context 'with no User logged in' do + before :each do + delete :destroy, :id => @subject.id + end + + it { should redirect_to new_user_session_path } + end + end + + describe 'index' do + before :each do + @subject = FactoryGirl.build(:mezuro_configuration) + MezuroConfiguration.expects(:all).returns([@subject]) + get :index + end + + it { should render_template(:index) } + end + + describe 'edit' do + before do + @subject = FactoryGirl.build(:mezuro_configuration) + end + + context 'with an User logged in' do + before do + @user = FactoryGirl.create(:user) + @ownership = FactoryGirl.build(:mezuro_configuration_ownership) + @ownerships = [] + + User.any_instance.expects(:mezuro_configuration_ownerships).at_least_once.returns(@ownerships) + + sign_in @user + end + + context 'when the user owns the mezuro_configuration' do + before :each do + MezuroConfiguration.expects(:find).with(@subject.id.to_s).returns(@subject) + @ownerships.expects(:find_by_mezuro_configuration_id).with("#{@subject.id}").returns(@ownership) + + get :edit, :id => @subject.id + end + + it { should render_template(:edit) } + + it 'should assign to @mezuro_configuration the @subject' do + assigns(:mezuro_configuration).should eq(@subject) + end + end + + context 'when the user does not own the mezuro_configuration' do + before do + @subject = FactoryGirl.build(:another_mezuro_configuration) + @ownerships.expects(:find_by_mezuro_configuration_id).with("#{@subject.id}").returns(nil) + + get :edit, :id => @subject.id + end + + it { should redirect_to(mezuro_configurations_path) } + it { should set_the_flash[:notice].to("You're not allowed to do this operation") } + end + end + + context 'with no user logged in' do + before :each do + get :edit, :id => @subject.id + end + + it { should redirect_to new_user_session_path } + end + end + + describe 'update' do + before do + @subject = FactoryGirl.build(:mezuro_configuration) + @subject_params = Hash[FactoryGirl.attributes_for(:mezuro_configuration).map { |k,v| [k.to_s, v.to_s] }] #FIXME: Mocha is creating the expectations with strings, but FactoryGirl returns everything with sybols and integers + end + + context 'when the user is logged in' do + before do + sign_in FactoryGirl.create(:user) + end + + context 'when user owns the mezuro_configuration' do + before do + @ownership = FactoryGirl.build(:mezuro_configuration_ownership) + @ownerships = [] + + @ownerships.expects(:find_by_mezuro_configuration_id).with("#{@subject.id}").returns(@ownership) + User.any_instance.expects(:mezuro_configuration_ownerships).at_least_once.returns(@ownerships) + end + + context 'with valid fields' do + before :each do + MezuroConfiguration.expects(:find).with(@subject.id.to_s).returns(@subject) + MezuroConfiguration.any_instance.expects(:update).with(@subject_params).returns(true) + end + + context 'rendering the show' do + before :each do + MezuroConfiguration.expects(:exists?).returns(true) + + post :update, :id => @subject.id, :mezuro_configuration => @subject_params + end + + it 'should redirect to the show view' do + response.should redirect_to mezuro_configuration_path(@subject) + end + end + + context 'without rendering the show view' do + before :each do + post :update, :id => @subject.id, :mezuro_configuration => @subject_params + end + + it { should respond_with(:redirect) } + end + end + + context 'with an invalid field' do + before :each do + MezuroConfiguration.expects(:find).with(@subject.id.to_s).returns(@subject) + MezuroConfiguration.any_instance.expects(:update).with(@subject_params).returns(false) + + post :update, :id => @subject.id, :mezuro_configuration => @subject_params + end + + it { should render_template(:edit) } + end + end + + context 'when the user does not own the mezuro_configuration' do + before :each do + post :update, :id => @subject.id, :mezuro_configuration => @subject_params + end + + it { should redirect_to mezuro_configurations_path } + end + end + + context 'with no user logged in' do + before :each do + post :update, :id => @subject.id, :mezuro_configuration => @subject_params + end + + it { should redirect_to new_user_session_path } + end + end +end diff --git a/spec/factories/mezuro_configuration_ownerships.rb b/spec/factories/mezuro_configuration_ownerships.rb index 0d1b4da..1c18992 100644 --- a/spec/factories/mezuro_configuration_ownerships.rb +++ b/spec/factories/mezuro_configuration_ownerships.rb @@ -3,6 +3,6 @@ FactoryGirl.define do factory :mezuro_configuration_ownership do user_id 1 - configuration_id 1 + mezuro_configuration_id 1 end end diff --git a/spec/models/mezuro_configuration_ownership_spec.rb b/spec/models/mezuro_configuration_ownership_spec.rb new file mode 100644 index 0000000..204c469 --- /dev/null +++ b/spec/models/mezuro_configuration_ownership_spec.rb @@ -0,0 +1,22 @@ +require 'spec_helper' + +describe MezuroConfigurationOwnership do + describe 'associations' do + it { should belong_to(:user) } + end + + describe 'methods' do + describe 'mezuro_configuration' do + subject {FactoryGirl.build(:mezuro_configuration_ownership)} + let(:mezuro_configuration) {FactoryGirl.build(:mezuro_configuration)} + + before :each do + MezuroConfiguration.expects(:find).with(subject.mezuro_configuration_id).returns(mezuro_configuration) + end + + it 'should return the mezuro_configuration' do + subject.mezuro_configuration.should eq(mezuro_configuration) + end + end + end +end diff --git a/spec/models/mezuro_configuration_spec.rb b/spec/models/mezuro_configuration_spec.rb index b2de81d..129d4a1 100644 --- a/spec/models/mezuro_configuration_spec.rb +++ b/spec/models/mezuro_configuration_spec.rb @@ -38,6 +38,17 @@ describe MezuroConfiguration do end end end + + describe 'metric_configurations' do + subject { FactoryGirl.build(:mezuro_configuration) } + let(:metric_configuration) { FactoryGirl.build(:metric_configuration) } + + it 'should call metric_configurations_of on the Metric Configuration model' do + KalibroGem::Entities::MetricConfiguration.expects(:metric_configurations_of).with(subject.id).returns([metric_configuration]) + + subject.metric_configurations.should include(metric_configuration) + end + end end describe 'validations' do diff --git a/spec/models/user_spec.rb b/spec/models/user_spec.rb index 4bdae09..226f83a 100644 --- a/spec/models/user_spec.rb +++ b/spec/models/user_spec.rb @@ -12,6 +12,7 @@ describe User do describe 'associations' do it { should have_many(:project_ownerships) } it { should have_many(:reading_group_ownerships) } + it { should have_many(:mezuro_configuration_ownerships) } end describe 'methods' do @@ -44,5 +45,20 @@ describe User do subject.reading_groups.should eq([reading_group]) end end + + describe 'mezuro_configurations' do + subject { FactoryGirl.build(:user) } + let(:mezuro_configuration) { FactoryGirl.build(:mezuro_configuration) } + let(:mezuro_configuration_ownership) { FactoryGirl.build(:mezuro_configuration_ownership) } + + before :each do + mezuro_configuration_ownership.expects(:mezuro_configuration).returns(mezuro_configuration) + subject.expects(:mezuro_configuration_ownerships).returns([mezuro_configuration_ownership]) + end + + it 'should return a list of mezuro configurations owned by the user' do + subject.mezuro_configurations.should eq([mezuro_configuration]) + end + end end end -- libgit2 0.21.2