ruby-grape / ruby-grape/grape

Customized Errors No Longer Including CORS Related Headers Upgrading from 1.0 to 1.3

Open
#2,078 5 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

bug?
Dominant language
Ruby
Stars
10k
Forks
1.2k
Avg merge
14h 38m
Merged PRs (30d)
92

Description

Steps to reproduce

What we need to do to see your problem or bug?

I've upgraded Grape from 1.0 to 1.3.3 and can no longer add Access-Control-Allow-Origin and Access-Control-Request-Method to the errors thrown by grape. I am using rescue_from :all to generate the desired status code for errors thrown by active record validations and other causes via this method as well.

    rescue_from :all do |error|
      error! error.message, FilmCal::Base.status_code_for(error, error.class.to_s), {
        'Access-Control-Allow-Origin' => '*',
        'Access-Control-Request-Method' => '*'
      }
    end

The errors throw with the correct status code in my specs BUT the customized headers are not being set.

The more detailed the issue, the more likely that we will fix it ASAP.

To get around the issue earlier on Grape 1.0 -- I returned a custom Rack::Response but AFTER upgrading to 1.3.3 this resulted in all of my specs receiving a 500 error with the message "Invalid Response":

  def self.cors_response_to_error(error)
    log_error(error)
    eclass = error.class.to_s
    message = "OAuth error: #{error}" if eclass =~ /WineBouncer::Errors/

    opts = prepare_opts(message, error, eclass)
    opts[:trace] = error.backtrace[0, 10] unless Rails.env.production?
    Rack::Response.new(opts.to_json, status_code_for(error, eclass),
                       'Content-Type' => 'application/json',
                       'Access-Control-Allow-Origin' => '*',
                       'Access-Control-Request-Method' => '*').finish
  end

So my thought was maybe this work around was no longer needed. However, I cannot get the standard error! method to honor the customized headers. Without them my client does not receive the errors returned by the server as they are no longer CORS.

Expected behavior

Tell us what should happen

The error response should have 'Access-Control-Allow-Origin' = '' and 'Access-Control-Request-Method' = ''.

Actual behavior

Tell us what happens instead

The headers were not present in the response with or without the explicit customization in the call to error!. All other responses (successfull responses) are receiving the custom headers via:

    before do
      header['Access-Control-Allow-Origin'] = '*'
      header['Access-Control-Request-Method'] = '*'
    end

It's only the errors that are not.

System configuration

You can help us to understand your problem if you will share some very
useful information about your project environment (don't forget to
remove any confidential data if it exists).
config.ru

# This file is used by Rack-based servers to start the application.
require 'rack'
require 'rack/cors'

use Rack::Cors do
    allow do
        origins '*'
        resource '*', headers: :any, methods: [:get, :post, :put, :patch, :delete, :options, :head]
    end
end

require_relative 'config/environment'

run Rails.application

Ruby version: ``
ruby '2.7.1'

Gemfile.lock:

Gemfile.lock content
GIT
  remote: https://github.com/antek-drzewiecki/wine_bouncer.git
  revision: c82b88f73c7adc43a8e89ca73f7e18952ec30de4
  specs:
    wine_bouncer (1.0.4)
      doorkeeper (>= 1.4, < 6.0)
      grape (>= 0.10)

GEM
  remote: https://rubygems.org/
  specs:
    actioncable (6.0.3.2)
      actionpack (= 6.0.3.2)
      nio4r (~> 2.0)
      websocket-driver (>= 0.6.1)
    actionmailbox (6.0.3.2)
      actionpack (= 6.0.3.2)
      activejob (= 6.0.3.2)
      activerecord (= 6.0.3.2)
      activestorage (= 6.0.3.2)
      activesupport (= 6.0.3.2)
      mail (>= 2.7.1)
    actionmailer (6.0.3.2)
      actionpack (= 6.0.3.2)
      actionview (= 6.0.3.2)
      activejob (= 6.0.3.2)
      mail (~> 2.5, >= 2.5.4)
      rails-dom-testing (~> 2.0)
    actionpack (6.0.3.2)
      actionview (= 6.0.3.2)
      activesupport (= 6.0.3.2)
      rack (~> 2.0, >= 2.0.8)
      rack-test (>= 0.6.3)
      rails-dom-testing (~> 2.0)
      rails-html-sanitizer (~> 1.0, >= 1.2.0)
    actiontext (6.0.3.2)
      actionpack (= 6.0.3.2)
      activerecord (= 6.0.3.2)
      activestorage (= 6.0.3.2)
      activesupport (= 6.0.3.2)
      nokogiri (>= 1.8.5)
    actionview (6.0.3.2)
      activesupport (= 6.0.3.2)
      builder (~> 3.1)
      erubi (~> 1.4)
      rails-dom-testing (~> 2.0)
      rails-html-sanitizer (~> 1.1, >= 1.2.0)
    active_model_serializers (0.10.10)
      actionpack (>= 4.1, < 6.1)
      activemodel (>= 4.1, < 6.1)
      case_transform (>= 0.2)
      jsonapi-renderer (>= 0.1.1.beta1, < 0.3)
    activejob (6.0.3.2)
      activesupport (= 6.0.3.2)
      globalid (>= 0.3.6)
    activemodel (6.0.3.2)
      activesupport (= 6.0.3.2)
    activerecord (6.0.3.2)
      activemodel (= 6.0.3.2)
      activesupport (= 6.0.3.2)
    activestorage (6.0.3.2)
      actionpack (= 6.0.3.2)
      activejob (= 6.0.3.2)
      activerecord (= 6.0.3.2)
      marcel (~> 0.3.1)
    activesupport (6.0.3.2)
      concurrent-ruby (~> 1.0, >= 1.0.2)
      i18n (>= 0.7, < 2)
      minitest (~> 5.1)
      tzinfo (~> 1.1)
      zeitwerk (~> 2.2, >= 2.2.2)
    acts_as_list (1.0.1)
      activerecord (>= 4.2)
    addressable (2.7.0)
      public_suffix (>= 2.0.2, < 5.0)
    ast (2.4.0)
    aws-eventstream (1.1.0)
    aws-partitions (1.334.0)
    aws-sdk-core (3.102.0)
      aws-eventstream (~> 1, >= 1.0.2)
      aws-partitions (~> 1, >= 1.239.0)
      aws-sigv4 (~> 1.1)
      jmespath (~> 1.0)
    aws-sdk-kms (1.35.0)
      aws-sdk-core (~> 3, >= 3.99.0)
      aws-sigv4 (~> 1.1)
    aws-sdk-lambda (1.45.0)
      aws-sdk-core (~> 3, >= 3.99.0)
      aws-sigv4 (~> 1.1)
    aws-sdk-s3 (1.70.0)
      aws-sdk-core (~> 3, >= 3.99.0)
      aws-sdk-kms (~> 1)
      aws-sigv4 (~> 1.1)
    aws-sdk-sns (1.26.0)
      aws-sdk-core (~> 3, >= 3.99.0)
      aws-sigv4 (~> 1.1)
    aws-sigv4 (1.2.1)
      aws-eventstream (~> 1, >= 1.0.2)
    bcrypt (3.1.13)
    benchmark-ips (2.7.2)
    bootsnap (1.4.6)
      msgpack (~> 1.0)
    builder (3.2.4)
    byebug (10.0.2)
    case_transform (0.2)
      activesupport
    choice (0.2.0)
    coderay (1.1.3)
    concurrent-ruby (1.1.6)
    connection_pool (2.2.3)
    crack (0.4.3)
      safe_yaml (~> 1.0.0)
    crass (1.0.6)
    daemons (1.3.1)
    database_cleaner (1.8.5)
    derailed_benchmarks (1.3.4)
      benchmark-ips (~> 2)
      get_process_mem (~> 0)
      heapy (~> 0)
      memory_profiler (~> 0)
      rack (>= 1)
      rake (> 10, < 13)
      thor (~> 0.19)
    devise (4.7.2)
      bcrypt (~> 3.0)
      orm_adapter (~> 0.1)
      railties (>= 4.1.0)
      responders
      warden (~> 1.2.3)
    diff-lcs (1.4.2)
    docile (1.3.2)
    doorkeeper (5.4.0)
      railties (>= 5)
    doorkeeper-jwt (0.4.0)
      jwt (~> 2.1)
    dotenv (2.7.5)
    dotenv-rails (2.7.5)
      dotenv (= 2.7.5)
      railties (>= 3.2, < 6.1)
    down (5.1.1)
      addressable (~> 2.5)
    dry-configurable (0.11.6)
      concurrent-ruby (~> 1.0)
      dry-core (~> 0.4, >= 0.4.7)
      dry-equalizer (~> 0.2)
    dry-container (0.7.2)
      concurrent-ruby (~> 1.0)
      dry-configurable (~> 0.1, >= 0.1.3)
    dry-core (0.4.9)
      concurrent-ruby (~> 1.0)
    dry-equalizer (0.3.0)
    dry-inflector (0.2.0)
    dry-logic (1.0.6)
      concurrent-ruby (~> 1.0)
      dry-core (~> 0.2)
      dry-equalizer (~> 0.2)
    dry-types (1.4.0)
      concurrent-ruby (~> 1.0)
      dry-container (~> 0.3)
      dry-core (~> 0.4, >= 0.4.4)
      dry-equalizer (~> 0.3)
      dry-inflector (~> 0.1, >= 0.1.2)
      dry-logic (~> 1.0, >= 1.0.2)
    erubi (1.9.0)
    eventmachine (1.2.7)
    factory_bot (6.0.2)
      activesupport (>= 5.0.0)
    factory_bot_rails (6.0.0)
      factory_bot (~> 6.0.0)
      railties (>= 5.0.0)
    faraday (1.0.1)
      multipart-post (>= 1.2, < 3)
    ffi (1.13.1)
    formatador (0.2.5)
    get_process_mem (0.2.5)
      ffi (~> 1.0)
    globalid (0.4.2)
      activesupport (>= 4.2.0)
    grape (1.3.3)
      activesupport
      builder
      dry-types (>= 1.1)
      mustermann-grape (~> 1.0.0)
      rack (>= 1.3.0)
      rack-accept
    grape-active_model_serializers (1.5.2)
      active_model_serializers (>= 0.10.0)
      grape (>= 0.8.0)
    grape_logging (1.8.3)
      grape
      rack
    guard (2.16.2)
      formatador (>= 0.2.4)
      listen (>= 2.7, < 4.0)
      lumberjack (>= 1.0.12, < 2.0)
      nenv (~> 0.1)
      notiffany (~> 0.0)
      pry (>= 0.9.12)
      shellany (~> 0.0)
      thor (>= 0.18.1)
    guard-rubocop (1.3.0)
      guard (~> 2.0)
      rubocop (~> 0.20)
    haml (5.0.4)
      temple (>= 0.8.0)
      tilt
    hashdiff (0.3.7)
    hashie (3.5.7)
    hashie-forbidden_attributes (0.1.1)
      hashie (>= 3.0)
    heapy (0.1.4)
    holidays (8.3.0)
    i18n (1.8.3)
      concurrent-ruby (~> 1.0)
    jaro_winkler (1.5.2)
    jmespath (1.4.0)
    json (2.3.0)
    jsonapi-renderer (0.2.2)
    jwt (2.2.1)
    launchy (2.4.3)
      addressable (~> 2.3)
    letter_opener (1.6.0)
      launchy (~> 2.2)
    listen (3.0.8)
      rb-fsevent (~> 0.9, >= 0.9.4)
      rb-inotify (~> 0.9, >= 0.9.7)
    loofah (2.6.0)
      crass (~> 1.0.2)
      nokogiri (>= 1.5.9)
    lumberjack (1.2.6)
    mail (2.7.1)
      mini_mime (>= 0.1.1)
    mailcatcher (0.2.4)
      eventmachine
      haml
      i18n
      json
      mail
      sinatra
      skinny (>= 0.1.2)
      sqlite3-ruby
      thin
    marcel (0.3.3)
      mimemagic (~> 0.3.2)
    memory_profiler (0.9.11)
    method_source (1.0.0)
    mimemagic (0.3.5)
    mini_mime (1.0.2)
    mini_portile2 (2.4.0)
    minitest (5.14.1)
    msgpack (1.3.3)
    multipart-post (2.1.1)
    mustermann (1.1.1)
      ruby2_keywords (~> 0.0.1)
    mustermann-grape (1.0.1)
      mustermann (>= 1.0.0)
    nenv (0.3.0)
    nio4r (2.5.2)
    nokogiri (1.10.9)
      mini_portile2 (~> 2.4.0)
    notiffany (0.1.3)
      nenv (~> 0.1)
      shellany (~> 0.0)
    orm_adapter (0.5.0)
    parallel (1.14.0)
    parser (2.6.0.0)
      ast (~> 2.4.0)
    pg (1.0.0)
    powerpack (0.1.2)
    pry (0.13.1)
      coderay (~> 1.1)
      method_source (~> 1.0)
    psych (3.1.0)
    public_suffix (4.0.5)
    puma (4.3.5)
      nio4r (~> 2.0)
    puma_worker_killer (0.1.1)
      get_process_mem (~> 0.2)
      puma (>= 2.7, < 5)
    rack (2.2.3)
    rack-accept (0.4.5)
      rack (>= 0.4)
    rack-cors (1.0.2)
    rack-protection (2.0.3)
      rack
    rack-test (1.1.0)
      rack (>= 1.0, < 3)
    rails (6.0.3.2)
      actioncable (= 6.0.3.2)
      actionmailbox (= 6.0.3.2)
      actionmailer (= 6.0.3.2)
      actionpack (= 6.0.3.2)
      actiontext (= 6.0.3.2)
      actionview (= 6.0.3.2)
      activejob (= 6.0.3.2)
      activemodel (= 6.0.3.2)
      activerecord (= 6.0.3.2)
      activestorage (= 6.0.3.2)
      activesupport (= 6.0.3.2)
      bundler (>= 1.3.0)
      railties (= 6.0.3.2)
      sprockets-rails (>= 2.0.0)
    rails-dom-testing (2.0.3)
      activesupport (>= 4.2.0)
      nokogiri (>= 1.6)
    rails-erd (1.5.2)
      activerecord (>= 3.2)
      activesupport (>= 3.2)
      choice (~> 0.2.0)
      ruby-graphviz (~> 1.2)
    rails-html-sanitizer (1.3.0)
      loofah (~> 2.3)
    rails_12factor (0.0.3)
      rails_serve_static_assets
      rails_stdout_logging
    rails_serve_static_assets (0.0.5)
    rails_stdout_logging (0.0.5)
    railties (6.0.3.2)
      actionpack (= 6.0.3.2)
      activesupport (= 6.0.3.2)
      method_source
      rake (>= 0.8.7)
      thor (>= 0.20.3, < 2.0)
    rainbow (3.0.0)
    rake (12.3.3)
    rb-fsevent (0.10.4)
    rb-inotify (0.10.1)
      ffi (~> 1.0)
    redis (4.0.3)
    responders (3.0.1)
      actionpack (>= 5.0)
      railties (>= 5.0)
    rspec-core (3.9.2)
      rspec-support (~> 3.9.3)
    rspec-expectations (3.9.2)
      diff-lcs (>= 1.2.0, < 2.0)
      rspec-support (~> 3.9.0)
    rspec-mocks (3.9.1)
      diff-lcs (>= 1.2.0, < 2.0)
      rspec-support (~> 3.9.0)
    rspec-rails (4.0.1)
      actionpack (>= 4.2)
      activesupport (>= 4.2)
      railties (>= 4.2)
      rspec-core (~> 3.9)
      rspec-expectations (~> 3.9)
      rspec-mocks (~> 3.9)
      rspec-support (~> 3.9)
    rspec-support (3.9.3)
    rspec_junit_formatter (0.4.1)
      rspec-core (>= 2, < 4, != 2.12.0)
    rubocop (0.65.0)
      jaro_winkler (~> 1.5.1)
      parallel (~> 1.10)
      parser (>= 2.5, != 2.5.1.1)
      powerpack (~> 0.1)
      psych (>= 3.1.0)
      rainbow (>= 2.2.2, < 4.0)
      ruby-progressbar (~> 1.7)
      unicode-display_width (~> 1.4.0)
    ruby-graphviz (1.2.3)
    ruby-progressbar (1.10.0)
    ruby2_keywords (0.0.2)
    safe_yaml (1.0.4)
    sentry-raven (3.0.0)
      faraday (>= 1.0)
    shellany (0.0.1)
    shoulda-matchers (4.3.0)
      activesupport (>= 4.2.0)
    sidekiq (5.2.9)
      connection_pool (~> 2.2, >= 2.2.2)
      rack (~> 2.0)
      rack-protection (>= 1.5.0)
      redis (>= 3.3.5, < 4.2)
    simplecov (0.18.5)
      docile (~> 1.1)
      simplecov-html (~> 0.11)
    simplecov-html (0.12.2)
    sinatra (2.0.3)
      mustermann (~> 1.0)
      rack (~> 2.0)
      rack-protection (= 2.0.3)
      tilt (~> 2.0)
    skinny (0.2.2)
      eventmachine (~> 1.0)
      thin
    spring (2.0.2)
      activesupport (>= 4.2)
    spring-watcher-listen (2.0.1)
      listen (>= 2.7, < 4.0)
      spring (>= 1.2, < 3.0)
    sprockets (4.0.2)
      concurrent-ruby (~> 1.0)
      rack (> 1, < 3)
    sprockets-rails (3.2.1)
      actionpack (>= 4.0)
      activesupport (>= 4.0)
      sprockets (>= 3.0.0)
    sqlite3 (1.3.13)
    sqlite3-ruby (1.3.3)
      sqlite3 (>= 1.3.3)
    stackprof (0.2.12)
    temple (0.8.0)
    thin (1.7.2)
      daemons (~> 1.0, >= 1.0.9)
      eventmachine (~> 1.0, >= 1.0.4)
      rack (>= 1, < 3)
    thor (0.20.3)
    thread_safe (0.3.6)
    tilt (2.0.9)
    timecop (0.9.1)
    tzinfo (1.2.7)
      thread_safe (~> 0.1)
    unicode-display_width (1.4.1)
    validates_email_format_of (1.6.3)
      i18n
    vcr (6.0.0)
    warden (1.2.8)
      rack (>= 2.0.6)
    webmock (3.4.2)
      addressable (>= 2.3.6)
      crack (>= 0.3.2)
      hashdiff
    websocket-driver (0.7.2)
      websocket-extensions (>= 0.1.0)
    websocket-extensions (0.1.5)
    zeitwerk (2.3.0)

PLATFORMS
  ruby

DEPENDENCIES
  active_model_serializers (~> 0.10.10)
  acts_as_list (~> 1.0.1)
  aws-sdk-core (~> 3)
  aws-sdk-lambda (~> 1)
  aws-sdk-s3 (~> 1)
  aws-sdk-sns (~> 1)
  bootsnap (>= 1.4.2)
  byebug
  database_cleaner
  derailed_benchmarks
  devise (~> 4.7.2)
  doorkeeper (~> 5.4.0)
  doorkeeper-jwt (~> 0.4.0)
  dotenv (~> 2.7.1)
  dotenv-rails (~> 2.7.1)
  down
  factory_bot_rails
  ffi (~> 1.13.1)
  grape (~> 1.3.3)
  grape-active_model_serializers (~> 1.5.2)
  grape_logging (~> 1.8.3)
  guard-rubocop
  hashie-forbidden_attributes
  holidays
  letter_opener
  listen (~> 3.0.5)
  mailcatcher
  pg
  puma (~> 4.1)
  puma_worker_killer
  rack-cors
  rails (~> 6.0.3, >= 6.0.3.2)
  rails-erd
  rails_12factor
  rake (~> 12.3.3)
  redis (~> 4.0.1)
  rspec-core
  rspec-expectations
  rspec-mocks
  rspec-rails (~> 4.0.0)
  rspec-support
  rspec_junit_formatter
  rubocop (~> 0.65.0)
  sentry-raven
  shoulda-matchers
  sidekiq
  simplecov
  spring
  spring-watcher-listen (~> 2.0.0)
  stackprof
  timecop
  tzinfo-data
  validates_email_format_of (~> 1.6.3)
  vcr
  webmock
  wine_bouncer!

RUBY VERSION
   ruby 2.7.1p83

BUNDLED WITH
   2.1.4

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start by tracing Grape 1.3.3's rescue_from and error! handling, using the issue's config.ru Rack::Cors setup and custom Rack::Response example as the reproduction. Verify whether customized error responses preserve Access-Control-Allow-Origin and Access-Control-Request-Method, and confirm the behavior with a focused regression test.

Written by the indexing model from the issue text.

Assessment

Tech stack
ruby
Domain
api
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Needs clarification
Newbie friendliness
30/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.