jpie 2.1.0 → 2.1.2

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b40ba16f3f137fa6f71b5f03a5aae566168c602ecab473c8804991a5b37ed70f
4
- data.tar.gz: ea9ba44be05ef07e7306ff0772377277f8f25eab9c199fbe2d3f7be7fc2477ac
3
+ metadata.gz: d80d347b9e33b07e48e743d38c6e8dce2423888c49f8b727b52c3f093b835d45
4
+ data.tar.gz: befcf097a0471378554ec98e328546be5426d812ac48ea2428da42b71221b783
5
5
  SHA512:
6
- metadata.gz: 216f53ac57192799de8c9864b72d19da9c9284600c4e6b5807ef3c1aca501986411a5a110cfd5ae862066ab033c9b8d85002cb1a1c5a9232129221d2228356d0
7
- data.tar.gz: d59596b504c0c69d9783ab590fdf70053ee7728def4ecc38902cb32f70d6313d81bfda425307bb8e0673e47daa808829df37e163cfe97c12767307ab29515ee9
6
+ metadata.gz: b01847d08978c2df2e270e36e231bbf21cfc93824a1c9519c2b982d819777050a21df3252183819f218c4d44b420f8161f9857c5add05900a663f11be87405b6
7
+ data.tar.gz: 8c89e6f2502308dddf7b72edffd8e58603bf664b7b6401ab9b7d100ad55024f25f2df46791b45d0097b6647a1de1fda7ef17363cc8ec83fd6f8e3691e2598302
@@ -20,6 +20,8 @@ Do NOT use when the cause is already known and verified, or for routine implemen
20
20
 
21
21
  **Find root cause before attempting fixes.** Quick patches mask underlying issues. If you are trying fixes without understanding why they might work, you are guessing—stop and investigate.
22
22
 
23
+ Do not change code just to pass specs, and do not change specs just to make them pass. Specs must test real functionality; both code and specs should be fixed so that they correctly reflect and verify the intended behaviour.
24
+
23
25
  ## Problem definition (observable symptom only)
24
26
 
25
27
  Define the problem in terms of **what is observed**, not assumed cause:
@@ -9,6 +9,8 @@ You are a systematic debugging specialist for the json_api gem (JPie). Your only
9
9
 
10
10
  **ALWAYS find root cause before attempting fixes.** Symptom fixes are failure. Quick patches mask underlying issues. If you are trying fixes without understanding why they might work, you are guessing—stop and investigate.
11
11
 
12
+ Do not recommend changing code just to pass specs, or changing specs just to make them pass. Specs must test real functionality; recommend fixes that make code and specs correctly reflect and verify intended behaviour.
13
+
12
14
  ## Four phases (complete in order)
13
15
 
14
16
  ### Phase 1: Investigation
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- jpie (2.1.0)
4
+ jpie (2.1.2)
5
5
  actionpack (~> 8.1, >= 8.1.0)
6
6
  pg_query (>= 4)
7
7
  prosopite (>= 1)
@@ -17,25 +17,27 @@ module JSONAPI
17
17
  end
18
18
 
19
19
  def self.find(resource_type, namespace: nil)
20
- return find_namespaced(resource_type, namespace) if namespace.present?
20
+ candidates = []
21
21
 
22
- find_flat(resource_type, namespace)
23
- end
22
+ # Namespaced resource, e.g. "widgets" with namespace "api/v1" → API::V1::WidgetResource
23
+ candidates << build_resource_class_name(resource_type, namespace) if namespace
24
24
 
25
- def self.find_namespaced(resource_type, namespace)
26
- namespaced_class = build_resource_class_name(resource_type, namespace)
27
- namespaced_class.constantize
28
- rescue NameError
29
- raise MissingResourceClass.new(resource_type, namespace:) unless JSONAPI.configuration.namespace_fallback
25
+ # Flat resource, e.g. "widgets" → WidgetResource
26
+ if !namespace || JSONAPI.configuration.namespace_fallback
27
+ candidates << build_resource_class_name(resource_type,
28
+ nil,)
29
+ end
30
30
 
31
- find_flat(resource_type, namespace)
31
+ resolve(candidates) || raise(MissingResourceClass.new(resource_type, namespace:))
32
32
  end
33
33
 
34
- def self.find_flat(resource_type, namespace)
35
- flat_class = build_resource_class_name(resource_type, nil)
36
- flat_class.constantize
37
- rescue NameError
38
- raise MissingResourceClass.new(resource_type, namespace:)
34
+ def self.find_for_model(model_class, namespace: nil)
35
+ return ActiveStorageBlobResource if active_storage_blob?(model_class)
36
+
37
+ effective_namespace = namespace || extract_namespace_from_model(model_class)
38
+ candidates = model_candidates(model_class, effective_namespace)
39
+
40
+ resolve(candidates) || raise(MissingResourceClass.new(model_class.name, namespace: effective_namespace))
39
41
  end
40
42
 
41
43
  def self.build_resource_class_name(resource_type, namespace)
@@ -45,35 +47,42 @@ module JSONAPI
45
47
  "#{namespace.to_s.camelize}::#{base}"
46
48
  end
47
49
 
48
- def self.find_for_model(model_class, namespace: nil)
49
- return ActiveStorageBlobResource if active_storage_blob?(model_class)
50
+ # Builds an ordered list of candidate class names for a model, including
51
+ # STI base class candidates as a fallback.
52
+ def self.model_candidates(model_class, namespace)
53
+ candidates = candidates_for_class(model_class, namespace)
50
54
 
51
- find_resource_for_model(model_class, namespace)
55
+ if sti_subclass?(model_class)
56
+ base = model_class.base_class
57
+ base_ns = extract_namespace_from_model(base) || namespace
58
+ candidates.concat(candidates_for_class(base, base_ns))
59
+ end
60
+
61
+ candidates
52
62
  end
53
63
 
54
- def self.find_resource_for_model(model_class, namespace)
55
- effective_namespace = namespace || extract_namespace_from_model(model_class)
64
+ def self.candidates_for_class(model_class, namespace)
56
65
  resource_type = model_class.name.demodulize.underscore.pluralize
66
+ candidates = []
57
67
 
58
- find(resource_type, namespace: effective_namespace)
59
- rescue MissingResourceClass
60
- try_flat_full_name_resource(model_class) || find_base_class_resource(model_class, effective_namespace)
61
- end
68
+ # Namespaced resource matching the model's namespace, e.g. API::V1::Widget → API::V1::WidgetResource
69
+ candidates << build_resource_class_name(resource_type, namespace) if namespace
62
70
 
63
- def self.try_flat_full_name_resource(model_class)
64
- return nil unless model_class.name.include?("::")
71
+ # Flat-combined name for namespaced models, e.g. Ticket::User → TicketUserResource
72
+ candidates << "#{model_class.name.gsub("::", "")}Resource" if model_class.name.include?("::")
65
73
 
66
- "#{model_class.name.gsub("::", "")}Resource".constantize
67
- rescue NameError
68
- nil
69
- end
74
+ # Standard flat resource using demodulized model name, e.g. User → UserResource
75
+ candidates << build_resource_class_name(resource_type, nil)
70
76
 
71
- def self.find_base_class_resource(model_class, effective_namespace)
72
- raise MissingResourceClass, model_class.name unless sti_subclass?(model_class)
77
+ candidates
78
+ end
73
79
 
74
- base_resource_type = model_class.base_class.name.demodulize.underscore.pluralize
75
- base_namespace = extract_namespace_from_model(model_class.base_class) || effective_namespace
76
- find(base_resource_type, namespace: base_namespace)
80
+ def self.resolve(candidates)
81
+ candidates.each do |name|
82
+ klass = name.safe_constantize
83
+ return klass if klass
84
+ end
85
+ nil
77
86
  end
78
87
 
79
88
  def self.active_storage_blob?(model_class)
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module JSONAPI
4
- VERSION = "2.1.0"
4
+ VERSION = "2.1.2"
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: jpie
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.1.0
4
+ version: 2.1.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Emil Kampp