eager_eye 0.1.0 → 0.2.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/CHANGELOG.md +15 -0
- data/README.md +32 -1
- data/lib/eager_eye/analyzer.rb +2 -1
- data/lib/eager_eye/configuration.rb +1 -1
- data/lib/eager_eye/version.rb +1 -1
- data/lib/eager_eye.rb +1 -0
- metadata +2 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 4adfe62f9c9082d1c0f1e9b149af5f2cc09db5a455af6c0262687a5770b2c50b
|
|
4
|
+
data.tar.gz: 5284a262cf22fc9e7191dafa0a45383b3f073565313e02d202fb902bc250e7bb
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: e40d5802cd52757817d3c6f071abb7203d05ca5b127a72ee5534066b59b4addb2fdec1a592f703864710eec81fa571ef774ada0cd2381995b3819b711366d939
|
|
7
|
+
data.tar.gz: 50d3bcfa2029032200cae2b4e05ba5ef319f1a981acfc1b8b2969e0dcd977d849d01c2edab51f42808d0bdda538a63be280ad2063f5927907b64e579185c223e
|
data/CHANGELOG.md
CHANGED
|
@@ -7,6 +7,21 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
7
7
|
|
|
8
8
|
## [Unreleased]
|
|
9
9
|
|
|
10
|
+
## [0.2.0] - 2025-12-15
|
|
11
|
+
|
|
12
|
+
### Added
|
|
13
|
+
|
|
14
|
+
- **New Detector: `CustomMethodQuery`** - Detects query methods called inside iteration blocks
|
|
15
|
+
- Catches `.where`, `.find_by`, `.find_by!`, `.exists?` patterns that Bullet cannot detect
|
|
16
|
+
- Detects `.find`, `.first`, `.last`, `.take` inside loops
|
|
17
|
+
- Detects aggregation methods: `.pluck`, `.ids`, `.count`, `.sum`, `.average`, `.minimum`, `.maximum`
|
|
18
|
+
- Provides suggestions for preloading data before loops
|
|
19
|
+
|
|
20
|
+
### Changed
|
|
21
|
+
|
|
22
|
+
- Updated default `enabled_detectors` to include `:custom_method_query`
|
|
23
|
+
- Updated README with new detector documentation and comparison table
|
|
24
|
+
|
|
10
25
|
## [0.1.0] - 2025-12-15
|
|
11
26
|
|
|
12
27
|
### Added
|
data/README.md
CHANGED
|
@@ -14,7 +14,7 @@ EagerEye analyzes your Ruby code without running it, using AST (Abstract Syntax
|
|
|
14
14
|
Unlike runtime tools like Bullet, EagerEye:
|
|
15
15
|
|
|
16
16
|
- **Runs without executing code** - Works in CI pipelines without a test suite
|
|
17
|
-
- **Catches more patterns** - Detects serializer N+1s
|
|
17
|
+
- **Catches more patterns** - Detects serializer N+1s, missing counter caches, and query methods in loops
|
|
18
18
|
- **Proactive detection** - Finds issues at code review time, not after deployment
|
|
19
19
|
|
|
20
20
|
| Feature | EagerEye | Bullet |
|
|
@@ -23,6 +23,7 @@ Unlike runtime tools like Bullet, EagerEye:
|
|
|
23
23
|
| Requires test suite | No | Yes |
|
|
24
24
|
| Serializer N+1 detection | Yes | Limited |
|
|
25
25
|
| Counter cache suggestions | Yes | No |
|
|
26
|
+
| Query methods in loops | Yes | No |
|
|
26
27
|
| CI integration | Native | Requires tests |
|
|
27
28
|
| False positive rate | Higher | Lower |
|
|
28
29
|
|
|
@@ -146,6 +147,35 @@ belongs_to :post, counter_cache: true
|
|
|
146
147
|
post.comments_count
|
|
147
148
|
```
|
|
148
149
|
|
|
150
|
+
### 4. Custom Method Query (N+1 in query methods)
|
|
151
|
+
|
|
152
|
+
Detects query methods (`.where`, `.find_by`, `.exists?`, etc.) called on associations inside loops. **These patterns are invisible to Bullet.**
|
|
153
|
+
|
|
154
|
+
```ruby
|
|
155
|
+
# Bad - Bullet CANNOT catch this
|
|
156
|
+
class User < ApplicationRecord
|
|
157
|
+
def supports?(team_name)
|
|
158
|
+
teams.where(name: team_name).exists?
|
|
159
|
+
end
|
|
160
|
+
end
|
|
161
|
+
|
|
162
|
+
@users.each do |user|
|
|
163
|
+
user.supports?("Lakers") # Query for each user!
|
|
164
|
+
end
|
|
165
|
+
|
|
166
|
+
# Bad - find_by inside loop
|
|
167
|
+
@orders.each do |order|
|
|
168
|
+
order.line_items.find_by(featured: true)
|
|
169
|
+
end
|
|
170
|
+
|
|
171
|
+
# Good - Preload and filter in Ruby
|
|
172
|
+
@users.includes(:teams).each do |user|
|
|
173
|
+
user.teams.any? { |t| t.name == "Lakers" }
|
|
174
|
+
end
|
|
175
|
+
```
|
|
176
|
+
|
|
177
|
+
**Detected methods:** `where`, `find_by`, `find_by!`, `exists?`, `find`, `first`, `last`, `take`, `pluck`, `ids`, `count`, `sum`, `average`, `minimum`, `maximum`
|
|
178
|
+
|
|
149
179
|
## Configuration
|
|
150
180
|
|
|
151
181
|
### Config File (.eager_eye.yml)
|
|
@@ -161,6 +191,7 @@ enabled_detectors:
|
|
|
161
191
|
- loop_association
|
|
162
192
|
- serializer_nesting
|
|
163
193
|
- missing_counter_cache
|
|
194
|
+
- custom_method_query
|
|
164
195
|
|
|
165
196
|
# Base path to analyze (default: app)
|
|
166
197
|
app_path: app
|
data/lib/eager_eye/analyzer.rb
CHANGED
|
@@ -7,7 +7,8 @@ module EagerEye
|
|
|
7
7
|
DETECTOR_CLASSES = {
|
|
8
8
|
loop_association: Detectors::LoopAssociation,
|
|
9
9
|
serializer_nesting: Detectors::SerializerNesting,
|
|
10
|
-
missing_counter_cache: Detectors::MissingCounterCache
|
|
10
|
+
missing_counter_cache: Detectors::MissingCounterCache,
|
|
11
|
+
custom_method_query: Detectors::CustomMethodQuery
|
|
11
12
|
}.freeze
|
|
12
13
|
|
|
13
14
|
attr_reader :paths, :issues
|
|
@@ -4,7 +4,7 @@ module EagerEye
|
|
|
4
4
|
class Configuration
|
|
5
5
|
attr_accessor :excluded_paths, :enabled_detectors, :app_path, :fail_on_issues
|
|
6
6
|
|
|
7
|
-
DEFAULT_DETECTORS = %i[loop_association serializer_nesting missing_counter_cache].freeze
|
|
7
|
+
DEFAULT_DETECTORS = %i[loop_association serializer_nesting missing_counter_cache custom_method_query].freeze
|
|
8
8
|
|
|
9
9
|
def initialize
|
|
10
10
|
@excluded_paths = []
|
data/lib/eager_eye/version.rb
CHANGED
data/lib/eager_eye.rb
CHANGED
|
@@ -7,6 +7,7 @@ require_relative "eager_eye/detectors/base"
|
|
|
7
7
|
require_relative "eager_eye/detectors/loop_association"
|
|
8
8
|
require_relative "eager_eye/detectors/serializer_nesting"
|
|
9
9
|
require_relative "eager_eye/detectors/missing_counter_cache"
|
|
10
|
+
require_relative "eager_eye/detectors/custom_method_query"
|
|
10
11
|
require_relative "eager_eye/analyzer"
|
|
11
12
|
require_relative "eager_eye/reporters/base"
|
|
12
13
|
require_relative "eager_eye/reporters/console"
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: eager_eye
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.
|
|
4
|
+
version: 0.2.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- hamzagedikkaya
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: exe
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2025-12-
|
|
11
|
+
date: 2025-12-15 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: ast
|