rails_settlement 1.1.0 → 1.3.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: c6cd260f7d833858f657cf7975bc54f27d9b96ac4683ceae6600b0ee404e5799
4
- data.tar.gz: 62504498246549f0742944144059d1a9bff5687f6a0f775a4ff80bb1a75c3440
3
+ metadata.gz: 8a6695df770d40dfaff82ecab8bc78d0c8094be1c1bb5396a3065627394d3b2a
4
+ data.tar.gz: 816e133bd3c262c8ca33f77b1d2629e11f3980a14a903111b93d22fb1c7d8f66
5
5
  SHA512:
6
- metadata.gz: 814545781be4df3a5e653ada67eef58ba81264f67bcfc1bab8591c19f4336e3f46051346dab13e9d7e34b6a0d81da75a1441359a67aa66e331193bcd185426f3
7
- data.tar.gz: f014d90ed48da27180bf93760dfe0483e300b79974059e3cced620d26932d22195b7661f7b17516b1519ab239e5c0d958cc55755df55ffbfb50fe49e00cd6fcd
6
+ metadata.gz: 0524dceb140d2e07286d2cac1adfde6d4c24a1b4f10b9103cd0509b0475551e263e14e2deb51c530961f8c5092ff06469723373eb1f391aaaaa862a26bbe311c
7
+ data.tar.gz: 2ffc3f8ddacc5ce63232670febdb4223f968760ce9da686c20553fd6cfc9b75150b7d2c9cbfffafe2cf865f4745b6a238a61c17ea70343d09085943bbca776a4
data/.rubocop.yml CHANGED
@@ -10,7 +10,7 @@ Style/StringLiteralsInInterpolation:
10
10
  EnforcedStyle: double_quotes
11
11
 
12
12
  Layout/LineLength:
13
- Max: 130
13
+ Max: 150
14
14
 
15
15
  Metrics/AbcSize:
16
16
  Max: 22
data/README.md CHANGED
@@ -9,34 +9,44 @@ Add to your Gemfile:
9
9
  gem 'rails_settlement'
10
10
  ```
11
11
 
12
- ## How to User
12
+ ## How to Use
13
13
 
14
- Let's suppose you want to fetch a `User` before performing a controller action:
14
+ Suppose you need to fetch a User before executing a controller action:
15
15
 
16
16
  ```ruby
17
17
  class UsersController < ApplicationController
18
- set_user only: %i[show] # Internally, it's just a before_action callback, so you can pass options to the callback directly.
19
- set_user! only: %i[edit] # Using this method with a bang (!) would trigger an ActiveRecord::RecordNotFound Exception.
18
+ set_user only: %i[show] # It's essentially a before_action callback, allowing you to pass options directly.
19
+
20
+ # Using the bang (!) with this method triggers an ActiveRecord::RecordNotFound Exception.
21
+ set_user! only: %i[edit]
22
+
23
+ # You can also define a scope with the `scope_to` option. It can be either a string/symbol or an Array of string/symbols.
24
+ # This fetches the user after chaining all the scopes together.
25
+ # set_user scope_to: :is_active, only: %i[show] #=> User.is_active.find_by
26
+ # set_user! scope_to: %i[is_active is_admin] #=> User.is_active.is_admin.find_by
20
27
 
21
28
  def show
22
- do_something with: user # You will also have an attribute reader with the same name available if the object is found. If not, it'll default to nil (unless a bang method is used, in which case an error is raised!)
29
+ do_something with: user # You also have an attribute reader with the same name available if the object is found. If not, it defaults to nil (unless a bang method is used, in which case an error is raised!)
23
30
  end
24
31
  end
25
32
  ```
26
33
 
27
34
  ```ruby
28
35
  class User < ApplicationRecord
29
- # This method would be used internally by set_user to fetch correct param (using params_key), and to send a key to #find_by (using model_key)
30
- # This can be also overridden on the fly by passing any of these two keys (or both!) in the controller directly
36
+ scope :is_active, -> { where(is_active: true) }
37
+
38
+ # This method is used internally by `set_user` to fetch the correct param (using `params_key`) and to send a key to `find_by` (using `model_key`).
39
+ # You can override this on the fly by passing any of these two keys (or both!) in the controller directly.
31
40
  # Ex: set_user params_key: :user_username, only: %i[index], ...
41
+ # You can also pass a `scope_to` option in the hash below.
32
42
  def self.settable_params
33
43
  { params_key: :username, model_key: :username }
34
44
  end
35
45
  end
36
46
  ```
37
47
 
38
- This way you can use any model instead of a `User`. Just follow the naming convention `set_[model_name_in_snake_case]!`.
48
+ This approach allows you to use any model instead of a `User`. Just follow the naming convention set_[model_name_in_snake_case]!.
39
49
 
40
- P.S: This should not work with STI or any Namespaced models. If you have a way to make them work, please raise a pull request!
50
+ Note: This implementation does not support STI or any Namespaced models. If you have a solution to make them work, please submit a pull request!
41
51
 
42
52
  That's about it!
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module RailsSettlement
4
- VERSION = "1.1.0"
4
+ VERSION = "1.3.0"
5
5
  end
@@ -10,19 +10,17 @@ module RailsSettlement
10
10
 
11
11
  SETTABLE_REGEX = /\Aset_(?<object>[a-z_]+)(?<raisable>!?)\z/.freeze
12
12
 
13
- class_methods do
13
+ class_methods do # rubocop:disable Metrics/BlockLength
14
14
  def method_missing(method, **options)
15
- super unless (match_data = method.to_s.match(SETTABLE_REGEX))
15
+ super unless (matches = method.to_s.match(SETTABLE_REGEX))
16
16
 
17
- variable = match_data[:object]
18
- raisable = match_data[:raisable].present?
19
-
20
- klass = variable.classify.constantize
21
-
22
- param_options = (klass.try(:settable_params) || {}).merge(options.extract!(:model_key, :params_key))
17
+ variable, raisable = _handle_match_data(matches)
18
+ klass = _klass(variable, **options.extract!(:namespace))
19
+ param_options = _param_options(klass: klass, options: options)
20
+ scoped_klass = _handle_scopes(klass: klass, scopes: param_options[:scope_to])
23
21
 
24
22
  before_action(**options) do
25
- instance_variable_set("@#{variable}", klass.find_by(param_options[:model_key] => params[param_options[:params_key]]))
23
+ instance_variable_set("@#{variable}", scoped_klass.find_by(param_options[:model_key] => params[param_options[:params_key]]))
26
24
  raise ActiveRecord::RecordNotFound if raisable && instance_variable_get("@#{variable}").nil?
27
25
  end
28
26
 
@@ -32,6 +30,31 @@ module RailsSettlement
32
30
  def respond_to_missing?(method, include_private = false)
33
31
  super || method.to_s.match?(SETTABLE_REGEX)
34
32
  end
33
+
34
+ private
35
+
36
+ def _handle_match_data(match_data)
37
+ [match_data[:object], match_data[:raisable].present?]
38
+ end
39
+
40
+ def _klass(variable, namespace: nil)
41
+ variable = variable.classify
42
+ variable = "#{namespace.to_s.classify}::#{variable}" if namespace.present?
43
+ variable.constantize
44
+ end
45
+
46
+ def _param_options(klass:, options:)
47
+ (klass.try(:settable_params) || {}).merge(options.extract!(:model_key, :params_key, :scope_to))
48
+ end
49
+
50
+ def _handle_scopes(klass:, scopes:)
51
+ return klass if scopes.blank?
52
+
53
+ scopes = [scopes] unless scopes.is_a?(Array)
54
+ scopes.each { |scope| klass = klass.public_send(scope) }
55
+
56
+ klass
57
+ end
35
58
  end
36
59
  end
37
60
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rails_settlement
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.0
4
+ version: 1.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tejas
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2024-02-10 00:00:00.000000000 Z
11
+ date: 2024-02-20 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activerecord