Skip to content

Commit 0c03b5d

Browse files
authored
fix(#2236): Stripping the internals of Grape::Endpoint when NoMethodError is raised (#2368)
* fix(#2236): Stripping the internals of `Grape::Endpoint` when `NoMethodError` is raised * fix(#2236): Follow quote ruby style and including the endpoint in the error message * fix(#2236): Running rubocop and applying corrections
1 parent 32b8d22 commit 0c03b5d

File tree

3 files changed

+33
-0
lines changed

3 files changed

+33
-0
lines changed

CHANGELOG.md

+1
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212

1313
* [#2364](https://github.com/ruby-grape/grape/pull/2364): Add missing requires - [@ericproulx](https://github.com/ericproulx).
1414
* [#2366](https://github.com/ruby-grape/grape/pull/2366): Default quality to 1.0 in the `Accept` header when omitted - [@hiddewie](https://github.com/hiddewie).
15+
* [#2368](https://github.com/ruby-grape/grape/pull/2368): Stripping the internals of `Grape::Endpoint` when `NoMethodError` is raised - [@jcagarcia](https://github.com/jcagarcia).
1516
* Your contribution here.
1617

1718
### 1.8.0 (2023/08/30)

lib/grape/endpoint.rb

+8
Original file line numberDiff line numberDiff line change
@@ -403,5 +403,13 @@ def options?
403403
options[:options_route_enabled] &&
404404
env[Grape::Http::Headers::REQUEST_METHOD] == Grape::Http::Headers::OPTIONS
405405
end
406+
407+
def method_missing(name, *_args)
408+
raise NoMethodError.new("undefined method `#{name}' for #{self.class} in `#{route.origin}' endpoint")
409+
end
410+
411+
def respond_to_missing?(method_name, include_private = false)
412+
super
413+
end
406414
end
407415
end

spec/grape/endpoint_spec.rb

+24
Original file line numberDiff line numberDiff line change
@@ -692,6 +692,30 @@ def app
692692
end
693693
end
694694

695+
describe '#method_missing' do
696+
context 'when referencing an undefined local variable' do
697+
it 'raises NoMethodError but stripping the internals of the Grape::Endpoint class and including the API route' do
698+
subject.get('/hey') do
699+
undefined_helper
700+
end
701+
expect do
702+
get '/hey'
703+
end.to raise_error(NoMethodError, %r{^undefined method `undefined_helper' for #<Class:0x[0-9a-fA-F]+> in `/hey' endpoint})
704+
end
705+
end
706+
707+
context 'when performing an undefined method of an instance inside the API' do
708+
it 'raises NoMethodError but stripping the internals of the Object class' do
709+
subject.get('/hey') do
710+
Object.new.x
711+
end
712+
expect do
713+
get '/hey'
714+
end.to raise_error(NoMethodError, /^undefined method `x' for #<Object:0x[0-9a-fA-F]+>$/)
715+
end
716+
end
717+
end
718+
695719
it 'does not persist params between calls' do
696720
subject.post('/new') do
697721
params[:text]

0 commit comments

Comments
 (0)