ErwinM / acts_as_tenant

Easy multi-tenancy for Rails in a shared database setup.
MIT License
1.56k stars 264 forks source link

Add a tenant change hook #333

Closed Winslett closed 8 months ago

Winslett commented 8 months ago

I've been looking to use ActsAsTenant in addition to Postgres's row-level security (RLS). With RLS, you can use a session variable to restrict the scope of queries to a single variable for a user. Then, the user would not be able to query all rows from a single query. In an attempt to keep ActsAsTenant as simple as possible, I think the best way to do this is a tenant_change_hook (or a similar pattern). This would allow a user to run a block of code each time the tenant is changed.

Using this tenant_change_hook, you could implement RLS with the following code block:

ActsAsTenant.configure do |config|
  config.tenant_change_hook = lambda do |tenant|
    if tenant.present?
      ActiveRecord::Base.connection.execute(ActiveRecord::Base.sanitize_sql_array(["SET rls.account_id = ?;", tenant.id]))
      Rails.logger.info "Changed tenant to " + [tenant.id, tenant.name].to_json
    end
  end
end

I've been around open source projects. Be harsh ;)

excid3 commented 8 months ago

Thanks @Winslett, this is a great addition. Looks like Standardrb flagged a couple things but after that it should be good to go.