rls_multi_tenant 0.3.1 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.rubocop.yml +1 -0
- data/CHANGELOG.md +11 -0
- data/README.md +23 -0
- data/lib/rls_multi_tenant/concerns/tenant_context.rb +29 -0
- data/lib/rls_multi_tenant/version.rb +1 -1
- metadata +1 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 9380863d6f5f1f68de3a4beaa1569cd6ad94bb5536604e0a444822628b946feb
|
|
4
|
+
data.tar.gz: eecebe1cecb827ed406b161f566de19d3effb7e8a96d73ebd497209b158e1c8b
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: faeb27cf2559a330bf13294cea3b114d017cb77d9c6e9af95acba26572bbf2016f6ffe2f8fb0dc67b1e731205f34f4ff0c69a4a592a91d6ec5d8b2c68127a211
|
|
7
|
+
data.tar.gz: 3fb38ae302313ed9845e86f3120c267ae88ad3e8eea793355f36db359ad316f6eaaac11805d21696a0b940ce54ba755cf5b4c5fdb7741066f1bd5b60fc236726
|
data/.rubocop.yml
CHANGED
data/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,17 @@ All notable changes to this project are documented in this file.
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## [0.4.0] - 2026-06-04
|
|
9
|
+
|
|
10
|
+
### Added
|
|
11
|
+
|
|
12
|
+
- **Apartment-style switching by a unique field.** `Tenant.switch_by(value)`
|
|
13
|
+
resolves the tenant by a unique column (defaulting to the configured
|
|
14
|
+
`subdomain_field`) and switches context for the block; pass `attribute:` to
|
|
15
|
+
use another column (e.g. `switch_by('acme', attribute: :slug)`). A permanent
|
|
16
|
+
`switch_by!` variant is also available. Both raise `RlsMultiTenant::Error`
|
|
17
|
+
when no tenant matches. Instance-level delegators are provided too.
|
|
18
|
+
|
|
8
19
|
## [0.3.1] - 2026-06-04
|
|
9
20
|
|
|
10
21
|
Corrects two bugs in the 0.3.0 security work, both uncovered by a new
|
data/README.md
CHANGED
|
@@ -152,6 +152,29 @@ Tenant.reset! # Reset context
|
|
|
152
152
|
current_tenant = Tenant.current
|
|
153
153
|
```
|
|
154
154
|
|
|
155
|
+
#### Switching by a unique field (Apartment-style)
|
|
156
|
+
|
|
157
|
+
Instead of a tenant object or id, switch by any unique column. The attribute
|
|
158
|
+
defaults to the configured `subdomain_field`:
|
|
159
|
+
|
|
160
|
+
```ruby
|
|
161
|
+
# Switch by subdomain (default field) for a block
|
|
162
|
+
Tenant.switch_by("company-a") do
|
|
163
|
+
User.create!(name: "User from Company A")
|
|
164
|
+
end
|
|
165
|
+
|
|
166
|
+
# Switch by another unique column
|
|
167
|
+
Tenant.switch_by("acme-inc", attribute: :slug) do
|
|
168
|
+
# ...
|
|
169
|
+
end
|
|
170
|
+
|
|
171
|
+
# Permanent variant (until reset!)
|
|
172
|
+
Tenant.switch_by!("company-a")
|
|
173
|
+
Tenant.reset!
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
`switch_by` raises `RlsMultiTenant::Error` when no tenant matches the value.
|
|
177
|
+
|
|
155
178
|
### Automatic Subdomain-Based Tenant Switching
|
|
156
179
|
|
|
157
180
|
The gem includes middleware that automatically switches tenants based on the request subdomain. This is enabled by default and works seamlessly with your tenant model.
|
|
@@ -60,6 +60,20 @@ module RlsMultiTenant
|
|
|
60
60
|
apply_tenant_context(tenant_id, local: false)
|
|
61
61
|
end
|
|
62
62
|
|
|
63
|
+
# Switch tenant context for a block, identifying the tenant by a unique
|
|
64
|
+
# field (Apartment-style). Defaults to the configured subdomain field.
|
|
65
|
+
#
|
|
66
|
+
# Tenant.switch_by('acme') { ... } # by subdomain
|
|
67
|
+
# Tenant.switch_by('acme', attribute: :slug) { } # by another column
|
|
68
|
+
def switch_by(value, attribute: RlsMultiTenant.subdomain_field, &block)
|
|
69
|
+
switch(find_tenant_by!(attribute, value), &block)
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
# Permanent variant of switch_by (until reset). Same caveats as switch!.
|
|
73
|
+
def switch_by!(value, attribute: RlsMultiTenant.subdomain_field)
|
|
74
|
+
switch!(find_tenant_by!(attribute, value))
|
|
75
|
+
end
|
|
76
|
+
|
|
63
77
|
# Reset tenant context
|
|
64
78
|
def reset!
|
|
65
79
|
connection.execute format(RESET_TENANT_ID_SQL, tenant_session_var)
|
|
@@ -81,6 +95,15 @@ module RlsMultiTenant
|
|
|
81
95
|
|
|
82
96
|
private
|
|
83
97
|
|
|
98
|
+
# Look up a tenant by a unique attribute, raising if none matches.
|
|
99
|
+
def find_tenant_by!(attribute, value)
|
|
100
|
+
tenant = RlsMultiTenant.tenant_class.find_by(attribute => value)
|
|
101
|
+
return tenant if tenant
|
|
102
|
+
|
|
103
|
+
raise RlsMultiTenant::Error,
|
|
104
|
+
"#{RlsMultiTenant.tenant_class_name} with #{attribute}=#{value.inspect} not found"
|
|
105
|
+
end
|
|
106
|
+
|
|
84
107
|
# Restore the previous context on the way out of a `switch` block.
|
|
85
108
|
# If the block aborted the transaction (e.g. a policy violation), any
|
|
86
109
|
# further statement raises until rollback; that rollback will clear the
|
|
@@ -142,8 +165,14 @@ module RlsMultiTenant
|
|
|
142
165
|
self.class.switch(tenant_or_id, &block)
|
|
143
166
|
end
|
|
144
167
|
|
|
168
|
+
def switch_by(value, attribute: RlsMultiTenant.subdomain_field, &block)
|
|
169
|
+
self.class.switch_by(value, attribute: attribute, &block)
|
|
170
|
+
end
|
|
171
|
+
|
|
145
172
|
delegate :switch!, to: :class
|
|
146
173
|
|
|
174
|
+
delegate :switch_by!, to: :class
|
|
175
|
+
|
|
147
176
|
delegate :reset!, to: :class
|
|
148
177
|
end
|
|
149
178
|
end
|