From 9e7e79394178f19be4aef9907a76fcabb13b079f Mon Sep 17 00:00:00 2001 From: benji Date: Mon, 23 Jan 2017 16:59:04 +0100 Subject: [PATCH 1/2] Add roles to clients --- Gemfile | 1 + Gemfile.lock | 2 ++ app/models/client.rb | 1 + app/models/client_ability.rb | 4 +++- app/models/role.rb | 12 +++++++++++ config/initializers/rolify.rb | 7 +++++++ .../20170123151219_rolify_create_roles.rb | 19 ++++++++++++++++++ db/schema.rb | 20 ++++++++++++++++++- spec/factories/roles.rb | 6 ++++++ spec/models/role_spec.rb | 5 +++++ 10 files changed, 75 insertions(+), 2 deletions(-) create mode 100644 app/models/role.rb create mode 100644 config/initializers/rolify.rb create mode 100644 db/migrate/20170123151219_rolify_create_roles.rb create mode 100644 spec/factories/roles.rb create mode 100644 spec/models/role_spec.rb diff --git a/Gemfile b/Gemfile index 69a2ade..d31482b 100644 --- a/Gemfile +++ b/Gemfile @@ -96,3 +96,4 @@ gem 'airbrake' gem 'bootstrap-sass', '~> 3.3.5' gem 'react-rails' +gem 'rolify' diff --git a/Gemfile.lock b/Gemfile.lock index c2323aa..2f608c8 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -223,6 +223,7 @@ GEM http-cookie (>= 1.0.2, < 2.0) mime-types (>= 1.16, < 3.0) netrc (~> 0.7) + rolify (5.1.0) rspec-core (3.3.2) rspec-support (~> 3.3.0) rspec-expectations (3.3.1) @@ -326,6 +327,7 @@ DEPENDENCIES purecss-rails rails (= 4.2.4) react-rails + rolify rspec-rails sass-rails (~> 5.0) sdoc (~> 0.4.0) diff --git a/app/models/client.rb b/app/models/client.rb index d8bd7da..c3f4762 100644 --- a/app/models/client.rb +++ b/app/models/client.rb @@ -10,6 +10,7 @@ # class Client < ActiveRecord::Base + rolify has_many :issued_transactions, as: :issuer, class_name: 'Transaction' before_create :generate_key diff --git a/app/models/client_ability.rb b/app/models/client_ability.rb index 1a5dd66..6e1fc77 100644 --- a/app/models/client_ability.rb +++ b/app/models/client_ability.rb @@ -3,6 +3,8 @@ class ClientAbility def initialize(client) client ||= Client.new # guest user (not logged in) - can :manage, :all + + can :create, Transaction if client.has_role? :create_transactions + can :create, Request end end diff --git a/app/models/role.rb b/app/models/role.rb new file mode 100644 index 0000000..7440b96 --- /dev/null +++ b/app/models/role.rb @@ -0,0 +1,12 @@ +class Role < ActiveRecord::Base + has_and_belongs_to_many :clients, join_table: :clients_roles + + belongs_to :resource, + polymorphic: true + + validates :resource_type, + inclusion: { in: Rolify.resource_types }, + allow_nil: true + + scopify +end diff --git a/config/initializers/rolify.rb b/config/initializers/rolify.rb new file mode 100644 index 0000000..25a2519 --- /dev/null +++ b/config/initializers/rolify.rb @@ -0,0 +1,7 @@ +Rolify.configure do |config| + # By default ORM adapter is ActiveRecord. uncomment to use mongoid + # config.use_mongoid + + # Dynamic shortcuts for User class (user.is_admin? like methods). Default is: false + # config.use_dynamic_shortcuts +end \ No newline at end of file diff --git a/db/migrate/20170123151219_rolify_create_roles.rb b/db/migrate/20170123151219_rolify_create_roles.rb new file mode 100644 index 0000000..8437240 --- /dev/null +++ b/db/migrate/20170123151219_rolify_create_roles.rb @@ -0,0 +1,19 @@ +class RolifyCreateRoles < ActiveRecord::Migration + def change + create_table(:roles) do |t| + t.string :name + t.references :resource, polymorphic: true + + t.timestamps + end + + create_table(:clients_roles, id: false) do |t| + t.references :client + t.references :role + end + + add_index(:roles, :name) + add_index(:roles, [ :name, :resource_type, :resource_id ]) + add_index(:clients_roles, [ :client_id, :role_id ]) + end +end diff --git a/db/schema.rb b/db/schema.rb index 3441a84..1ba8749 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -11,7 +11,7 @@ # # It's strongly recommended that you check this file into your version control system. -ActiveRecord::Schema.define(version: 20170109150245) do +ActiveRecord::Schema.define(version: 20170123151219) do create_table "clients", force: :cascade do |t| t.string "name", null: false @@ -23,6 +23,13 @@ ActiveRecord::Schema.define(version: 20170109150245) do add_index "clients", ["key"], name: "index_clients_on_key" add_index "clients", ["name"], name: "index_clients_on_name" + create_table "clients_roles", id: false, force: :cascade do |t| + t.integer "client_id" + t.integer "role_id" + end + + add_index "clients_roles", ["client_id", "role_id"], name: "index_clients_roles_on_client_id_and_role_id" + create_table "notifications", force: :cascade do |t| t.integer "user_id", null: false t.string "message" @@ -49,6 +56,17 @@ ActiveRecord::Schema.define(version: 20170109150245) do add_index "requests", ["debtor_id"], name: "index_requests_on_debtor_id" add_index "requests", ["issuer_type", "issuer_id"], name: "index_requests_on_issuer_type_and_issuer_id" + create_table "roles", force: :cascade do |t| + t.string "name" + t.integer "resource_id" + t.string "resource_type" + t.datetime "created_at" + t.datetime "updated_at" + end + + add_index "roles", ["name", "resource_type", "resource_id"], name: "index_roles_on_name_and_resource_type_and_resource_id" + add_index "roles", ["name"], name: "index_roles_on_name" + create_table "transactions", force: :cascade do |t| t.integer "debtor_id", null: false t.integer "creditor_id", null: false diff --git a/spec/factories/roles.rb b/spec/factories/roles.rb new file mode 100644 index 0000000..3ae14f9 --- /dev/null +++ b/spec/factories/roles.rb @@ -0,0 +1,6 @@ +FactoryGirl.define do + factory :role do + + end + +end diff --git a/spec/models/role_spec.rb b/spec/models/role_spec.rb new file mode 100644 index 0000000..41d4060 --- /dev/null +++ b/spec/models/role_spec.rb @@ -0,0 +1,5 @@ +require 'rails_helper' + +RSpec.describe Role, type: :model do + pending "add some examples to (or delete) #{__FILE__}" +end From 0a3c949d099c0333147635257378e198a76cfb3f Mon Sep 17 00:00:00 2001 From: benji Date: Mon, 23 Jan 2017 17:22:29 +0100 Subject: [PATCH 2/2] Fix tests --- spec/apis/transactions_controller_spec.rb | 81 ++++++++++++++--------- 1 file changed, 49 insertions(+), 32 deletions(-) diff --git a/spec/apis/transactions_controller_spec.rb b/spec/apis/transactions_controller_spec.rb index 890c21b..6999b82 100644 --- a/spec/apis/transactions_controller_spec.rb +++ b/spec/apis/transactions_controller_spec.rb @@ -1,4 +1,9 @@ describe TransactionsController, type: :api do + def post_transaction(extra_attributes = {}) + post '/transactions', { transaction: @api_attributes.merge(extra_attributes) }, + { 'HTTP_ACCEPT' => "application/json", "HTTP_AUTHORIZATION" => "Token token=#{@key}" } + end + before :each do @debtor = create :user @creditor = create :user @@ -14,43 +19,55 @@ describe TransactionsController, type: :api do @key = @client.key end - def post_transaction(extra_attributes = {}) - post '/transactions', { transaction: @api_attributes.merge(extra_attributes) }, - { 'HTTP_ACCEPT' => "application/json", "HTTP_AUTHORIZATION" => "Token token=#{@key}" } - end - - describe "Authentication" do - it "should require a client authentication key" do - post '/transactions' - expect(last_response.status).to eq(302) + describe 'with key' do + before :each do + @client.add_role :create_transactions end - it "should work with valid key" do - post_transaction - expect(last_response.status).to eq(201) + def post_transaction(extra_attributes = {}) + post '/transactions', { transaction: @api_attributes.merge(extra_attributes) }, + { 'HTTP_ACCEPT' => "application/json", "HTTP_AUTHORIZATION" => "Token token=#{@key}" } + end + + describe "Authentication" do + it "should require a client authentication key" do + post '/transactions' + expect(last_response.status).to eq(302) + end + + it "should work with valid key" do + post_transaction + expect(last_response.status).to eq(201) + end + end + + describe "successfull creating transaction" do + it "should create a transaction" do + expect { post_transaction }.to change { Transaction.count }.by(1) + end + + it "should set issuer" do + post_transaction + @transaction = Transaction.last + expect(@transaction.issuer).to eq(@client) + end + end + + describe "failed creating transaction" do + # it "should create a transaction" do + # expect { post_transaction(euros: -5) }.to change { Transaction.count }.by(0) + # end + + # it "should give 422 status" do + # post_transaction(euros: -4) + # expect(last_response.status).to eq(422) + # end end end - describe "successfull creating transaction" do - it "should create a transaction" do - expect { post_transaction }.to change { Transaction.count }.by(1) + describe 'without key' do + it "should not create a transaction" do + expect { post_transaction }.to_not change { Transaction.count } end - - it "should set issuer" do - post_transaction - @transaction = Transaction.last - expect(@transaction.issuer).to eq(@client) - end - end - - describe "failed creating transaction" do - # it "should create a transaction" do - # expect { post_transaction(euros: -5) }.to change { Transaction.count }.by(0) - # end - - # it "should give 422 status" do - # post_transaction(euros: -4) - # expect(last_response.status).to eq(422) - # end end end