Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support Postgresql json/jsonb columns #875

Open
23tux opened this issue Jan 19, 2025 · 0 comments
Open

Support Postgresql json/jsonb columns #875

23tux opened this issue Jan 19, 2025 · 0 comments

Comments

@23tux
Copy link

23tux commented Jan 19, 2025

I'd love to try for a PR, maybe someone can give me some guidance where to start:

We have a table with a jsonb column, that has a GIN index on it and stores various information. I'd like to define abilities based on fields inside that jsonb column.

How would one implement such a feature in cancancan? I know that I can pass scopes to abilities, but that doesn't solve calls like can?(:index, product) and they are not mergeable. So supporting jsonb columns the same way normale columns are supported would be awesome.

This gist should describe what I want to achieve:

require "bundler/inline"

gemfile(true) do
  source "https://rubygems.org"
  gem "rails", "= 7.1.5.1"
  gem "cancancan", "= 3.6.1", require: false # require false to force rails to be required first
end

require "active_record"
require "cancancan"
require "minitest/autorun"
require "logger"

ActiveRecord::Base.establish_connection(
  adapter: "postgresql",
  database: "test",
  username: "postgres",
  password: "password",
  host: "localhost"
)
ActiveRecord::Base.logger = Logger.new(STDOUT)

ActiveRecord::Schema.define do
  drop_table :products, if_exists: true
  create_table :products, force: true do |t|
    t.jsonb :data
  end
end

class Product < ActiveRecord::Base; end

class Ability
  include CanCan::Ability

  def initialize
    can :index, Product, data: { shop_id: 1 }
  end
end

class BugTest < Minitest::Test
  def test_bug
    product = Product.create!(data: { shop_id: 1 })
    ability = Ability.new
    assert_equal [product], Product.accessible_by(ability, :index).to_a
  end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant