• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

ruby-grape / grape
97%
master: 97%

Build:
Build:
LAST BUILD BRANCH: fix/adversarial-sweep-2026-08
DEFAULT BRANCH: master
Repo Added 04 Apr 2013 06:08AM UTC
Files 167
Badge
Embed ▾
README BADGES
x

If you need to use a raster PNG badge, change the '.svg' to '.png' in the link

Markdown

Textile

RDoc

HTML

Rst

LAST BUILD ON BRANCH fix/path-param-encoding
branch: fix/path-param-encoding
CHANGE BRANCH
x
Reset
  • fix/path-param-encoding
  • DateFormat
  • Handle_json_array
  • ISSUE-2321
  • Issue-1908
  • active_support_6_1_minimal
  • add-agents-md
  • add_irb_in_gemfile_for_bundle_console_warning
  • add_numericality_validator
  • add_rack_3_2_gemfile
  • add_rails_8_1_on_ci
  • add_ruby_3_4
  • add_ruby_4_0_cli
  • api_override_singleton_methods
  • array-param-regression
  • benchmark/results-machine-spec
  • body-metadata
  • bugfix/1577
  • bugfix/1970
  • bugfix/1986
  • bugfix/2041
  • bugfix/autoload
  • bugfix/memory-leak
  • build_with_registry
  • chore/agents-md-style-rules
  • chore/cleanup-on-compilation
  • chore/coercion-tests
  • chore/drop-middleware-globals
  • chore/guard-clause-cleanup
  • chore/json-parse-fallback
  • chore/min-ruby-3.3
  • chore/normalize-eql-aliases
  • chore/primitive-coercer-spec
  • chore/prune-requires
  • chore/raise-dependency-lower-bounds
  • chore/readability-guard-clauses
  • chore/readability-pass
  • clean_up_useless_dependencies
  • cleanup-deprecated-code
  • compiled_endpoints
  • contract_scope_validator_public_schema
  • cookies_delegation
  • crush_desclared_params
  • custom-validator-namespace-lookup
  • declared_params_optional_array
  • deprecated_endpoint_return
  • doc
  • doc/remove_manual_toc_and_toc_danger_check
  • doc/remove_toc
  • doc/update_reload_documentation_for_current_Rails_versions
  • docs/format-removal-note
  • docs/readme-typos-and-fixnum-cleanup
  • draft/middleware-options-data
  • drop_namespace_description
  • drop_ruby_3_0_as_7_0
  • drop_support_ruby_2_7_0
  • dynamic_registration
  • empty_string_and_bool
  • enable_branch_coverage
  • enable_frozen_string_literal_ci
  • endpoint_api_kwarg
  • endpoint_app_kwarg
  • endpoint_cleanup
  • endpoint_http_methods_kwarg
  • endpoint_path_kwarg
  • entity-dsl
  • eql-hash-consistency
  • erik/remove-faulty-documentation-about-blank-values
  • exclude_ruby_3_2_rails_edge
  • explicit_route_options
  • exposes-to-s
  • extract_entity_dsl_and_kwargs_with
  • extract_testing_module
  • extract_translation
  • failing_spec_for_1967
  • faster_normalize_path
  • feature/endpoint-logger
  • feature/error-formatter-kwargs-2527
  • feature/grape-api-setup-var-array
  • feature/hash-oneof-2385
  • feature/return_of_return
  • feature/warn-on-helper-overrides
  • feature_rack_lint
  • fix-636
  • fix-badges
  • fix-before-each-nil-nomethoderror
  • fix-cascade-dsl-getter
  • fix-coercer-request-time-state
  • fix-compile-instance-race
  • fix-docs
  • fix-helper-inheritance
  • fix-line-anchored-regexes
  • fix-multiple-type-values-check
  • fix-options-const-defined-object-fallback
  • fix-path-versioner-root-version
  • fix-router-cascade-routing-args
  • fix-router-cascade-sibling-routes
  • fix-top-level-entity-constant
  • fix-typo
  • fix-validator-non-hash-guard
  • fix/2748-structured-message-leak
  • fix/2763-multijson-deprecations
  • fix/auth-base-subclass-issue-2669
  • fix/avoid_multiple_mounts_pollution
  • fix/base-only-rescue-handlers
  • fix/cascade_reading_api_level
  • fix/case-insensitive-media-types
  • fix/custom-type-coercer-symbolize-collection
  • fix/entity-lookup-own-class-first
  • fix/error-rendering-failsafe
  • fix/grape-exceptions-precedence
  • fix/json-load-create-additions
  • fix/json-use-parse
  • fix/multixml-deprecation
  • fix/nested-array-validation-bypass
  • fix/recompile-after-route-added
  • fix/recompile-settings-mutation-race
  • fix/redirect-plain-text-body
  • fix/reduce_base_route_array_allocation
  • fix/rescue-from-internal-errors-2482
  • fix/router-request-time-map-mutation
  • fix/sendfile_test_fix
  • fix/stackable-copy-aliasing
  • fix/variant-collection-coercer-to-s
  • fix/warn-shadowed-rescue-from
  • fix_2566_memory_leak
  • fix_all_media_types_regression
  • fix_before_each_no_method_error
  • fix_coercer_cache
  • fix_danger_workflow
  • fix_endpoint_status_when_not_calling_error!
  • fix_gh_workflow_annotations_warnings
  • fix_helpers_methods_in_public_scope
  • fix_leaky_slash
  • fix_middleware_keywords
  • fix_param_scope_thread_safety
  • fix_registry_warning_message
  • fix_require_logger
  • fix_routes_memoization
  • fix_shared_params_empty_args
  • fix_style_optional_boolean_parameter
  • format_header_best_q_match
  • forward_match_kwarg
  • freeze-coercers-and-sync-caches
  • funding
  • happy_rubocop
  • head_route_on_route_class
  • hook-readme
  • inheritable-setting-auth-params-builder
  • inheritable-setting-callbacks
  • inheritable-setting-cheap-equality
  • inheritable-setting-content-negotiation
  • inheritable-setting-contract-key-map
  • inheritable-setting-finale
  • inheritable-setting-format-defaults
  • inheritable-setting-integration
  • inheritable-setting-middleware-helpers
  • inheritable-setting-params-state
  • inheritable-setting-representations
  • inheritable-setting-rescue-options
  • inheritable-setting-routing-flags
  • inheritable-setting-routing-scopes
  • inheritable-setting-versioning
  • instance-to-s-nil-fallback
  • instance_to_s_delegation
  • internalize-stackable-storage
  • issue-1775
  • issue-2385
  • layer1-thread-safety-invariants
  • layer2-concurrency-stress
  • lazy_block
  • lazy_compile
  • less_active_support_concern
  • less_parse_nested_query
  • master
  • migrate-danger-pr-comment
  • migrate-to-dry-configurable
  • mountable_apis
  • namespace_route_param_explicit_kwargs
  • optimize/parameters-extract-options-non-mutating
  • optimize_api_documentation
  • patch-1
  • perf/avoid-empty-hash-merges
  • perf/build-headers-each-header
  • perf/instrument-only-when-subscribed
  • perf/lazy-base-inheritable-new-values
  • perf/lazy-inheritable-setting-fields
  • perf/lazy-param-scope-tracker
  • perf/lazy-response-cookies
  • perf/precompute-middleware-caches
  • perf/request-hot-path-polish
  • perf/router-transaction-no-proc
  • perf/routing-args-in-place-merge
  • perf/skip-empty-validation-errors-alloc
  • perf/skip-redundant-routing-args-write
  • perf/skip-validation-backtrace
  • perf/stackable-empty-singleton
  • perf/versioner-path-prefix
  • private_namespace_reverse_stackable_with_hash
  • private_within_namespace
  • rack_request_error
  • real-api-integration-test
  • reduce_array_alloc_on_setup
  • refactor/api-instance-dsl-modules
  • refactor/attrs_iterator
  • refactor/auth-dsl-kwargs
  • refactor/available-media-types-attr-reader
  • refactor/base-validator-encapsulation
  • refactor/coerce-options-data
  • refactor/de-morgan-conditions
  • refactor/declared-params-handler
  • refactor/declared_availability
  • refactor/define-method-cleanup
  • refactor/drop-indifferent-and-reverse-merge-requires
  • refactor/dsl-group-validators-dry
  • refactor/encapsulate-reverse-stackable
  • refactor/endpoint-options-data
  • refactor/endpoint-options-route-enabled
  • refactor/error-response-data
  • refactor/error-response-value-object
  • refactor/extract-handler-case-when
  • refactor/extract-path-normalizer
  • refactor/guard-clauses-style
  • refactor/inline-mustermann-grape
  • refactor/lazy-base-ancestor
  • refactor/middleware-cleanups
  • refactor/mountable-marker
  • refactor/named_kwargs_params_scope
  • refactor/nest-path-in-pattern
  • refactor/params-dsl-using-except-kwargs
  • refactor/precomputed-content-types-move
  • refactor/replace-tap-usages
  • refactor/rescue-from-explicit-first-arg
  • refactor/rescue-handler-dedup
  • refactor/router-pattern-delegation
  • refactor/router-simplification
  • refactor/shared-options-data
  • refactor/stateless-attributes-iterator
  • refactor/validates-pure-helpers
  • refactor/validation-errors-drop-enumerable
  • refactor/validations-spec-self-validate
  • refactor/version-guard-clause
  • refactor_available_media_types_in_header_middleware
  • refactor_declared_params_handling
  • refactor_http_headers
  • refactor_mime_type_for
  • refactor_route_setting_internal_usage
  • refactor_setting_get_or_set
  • refs/heads/master
  • refs/tags/v1.7.1
  • refs/tags/v1.8.0
  • refs/tags/v2.0.0
  • regression/json-error-formatter-double-wrap
  • release/3.2.1
  • remove-inheritable-values
  • remove-reverse-stackable-values
  • remove-unused-constant
  • remove/http-digest-dsl
  • remove_deprecated_param_builder_extensions
  • remove_guard
  • remove_instance_variable_defined
  • remove_namespace_reverse_stackable_from_public_interface
  • remove_namespace_stackable_and_inheritable_from_public_space
  • remove_namespace_stackable_with_hash_from_public_interface
  • remove_non_supported_jsonapi
  • remove_obsolete_docker_compose_version
  • remove_path_dup
  • remove_pattern_format
  • remove_settings_unset_functions
  • remove_strict_hash_configuration
  • remove_test_prof
  • replace_try_by_respond_to
  • rescue_from
  • resolve_performace_issue_with_given
  • restore-routing-args-per-attempt
  • revert-1953-chore/micto-optimization-3
  • revert-2726-refactor/stateless-attributes-iterator
  • revert-2774-forward_match_kwarg
  • revert-wrong-commit
  • revisit_auth_middleware
  • revisit_endpoint_helpers_and_new
  • revisit_middleware_default_options
  • revisit_validators
  • robust_mounted_app_comparison
  • route-scope-accessors
  • route_attributes_kwargs
  • route_match_params_via_pattern
  • ruby3_handling_argument_delegation
  • ruby_3_1_shorthand_kwargs
  • ruby_optimizations
  • ruby_style_send
  • security/mounted-rack-auth-and-html-escape
  • skip_instrumentation_no_validators
  • skip_run_filters_on_empty
  • small_refactor_versioner_middleware
  • spec-only-rack-class
  • support-open-ranges-values
  • test-adversarial-nesting-depth
  • test/grape-swagger-integration
  • try_pattern_instead_of_respond_to
  • untangle_route_params
  • update_min_ruby_version_and_rubocop
  • update_return_upgrading_notes_and_simplify_execute
  • update_rubocop
  • update_rubocop_1_71_2
  • update_rubocop_1_88
  • update_rubocop_and_autocorrect
  • upgrade-mustermann
  • upgrade-rubocop
  • upgrading-array-unknown-element-type
  • upgrading-description
  • use_forwardable
  • use_require_relative_in_gemspec
  • v0.19.2
  • v1.0.0
  • v1.0.1
  • v1.0.2
  • v1.0.3
  • v1.1.0
  • v1.2.0
  • v1.2.1
  • v1.2.2
  • v1.2.3
  • v1.2.4
  • v1.2.5
  • v1.3.0
  • v1.3.1
  • v1.3.2
  • v1.3.3
  • v1.4.0
  • v1.5.0
  • v1.5.1
  • v2.1.0
  • v2.1.1
  • v2.1.2
  • v2.1.3
  • v2.2.0
  • v2.3.0
  • v2.4.0
  • v3.0.0
  • v3.0.1
  • v3.1.0
  • v3.1.1
  • v3.2.0
  • v3.2.1
  • v3.3.0
  • v3.3.1
  • v3.3.1_release
  • v3.3.2
  • v3.3.2_release
  • v3.3.3
  • v3.3.3_release
  • v3.3.4
  • v3.3.4_release
  • v3.3.5
  • v3.3.5_release
  • valid_encoding_before_scrubing
  • validators_bad_encoding

01 Aug 2026 08:15PM UTC coverage: 96.964% (-0.01%) from 96.976%
30716593749

Pull #2839

github

ericproulx
Tag path params as UTF-8 instead of leaving them binary

Mustermann decodes path captures out of PATH_INFO, which Rack hands over
tagged ASCII-8BIT, and nothing re-tagged the result. Query and body params
arrive UTF-8 because Rack tags those itself, so the same value reached the
endpoint with a different encoding depending on where it came from.

That made an API's declarations disagree with themselves -- a binary string
never equals the UTF-8 literal it was written as:

    params { requires :id, type: String, values: ['café'] }

    GET /?id=café   ->  200
    GET /café       ->  400 "id does not have a valid value"

The same held for same_as, except_values and any comparison an endpoint made
against a non-ASCII literal. It also leaked into serialization: a non-ASCII
path param rendered into a JSON response drew an encoding warning from the
json gem, which that gem says will become an error in json 3.0.

Re-tag in Route#params_for, the single funnel for path-extracted values.

Nothing obliges a client to send UTF-8 -- HTTP treats the request target as
octets, and Rack's SPEC has CGI keys carry non-ASCII as ASCII-8BIT -- so
UTF-8 is the convention rather than a guarantee: it is what browsers
percent-encode with, what an IRI maps to, and what Rails settles on
(ActionDispatch::Journey::Router force_encodes every path capture to UTF-8
after unescaping it). Only the encoding changes here: the bytes are
untouched, so octets that are not UTF-8 stay invalid and are still caught
downstream instead of being silently scrubbed into something the client
never sent. Unnamed splats capture into an Array, so those are walked too.

No extra allocations -- the captures are freshly built and unfrozen, so the
re-tag happens in place.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Pull Request #2839: Tag path params as UTF-8 instead of leaving them binary

1202 of 1291 branches covered (93.11%)

Branch coverage included in aggregate %.

6 of 7 new or added lines in 1 file covered. (85.71%)

1 existing line in 1 file now uncovered.

3812 of 3880 relevant lines covered (98.25%)

26780.64 hits per line

Relevant lines Covered
Build:
Build:
3880 RELEVANT LINES 3812 COVERED LINES
26780.64 HITS PER LINE
Source Files on fix/path-param-encoding
  • Tree
  • List 167
  • Changed 2
  • Source Changed 1
  • Coverage Changed 2
Coverage ∆ File Lines Relevant Covered Missed Hits/Line Branch Hits Branch Misses

Recent builds

Builds Branch Commit Type Ran Committer Via Coverage
30716593749 fix/path-param-encoding Tag path params as UTF-8 instead of leaving them binary Mustermann decodes path captures out of PATH_INFO, which Rack hands over tagged ASCII-8BIT, and nothing re-tagged the result. Query and body params arrive UTF-8 because Rack tags those itsel... Pull #2839 01 Aug 2026 08:16PM UTC ericproulx github
96.96
30704695691 fix/path-param-encoding Merge 720e518d7 into 32e481451 Pull #2839 01 Aug 2026 02:53PM UTC GitHub github
96.96
30704694487 fix/path-param-encoding Tag path params as UTF-8 instead of leaving them binary push 01 Aug 2026 02:52PM UTC Eric Proulx github
96.96
30697267026 fix/path-param-encoding Merge 2fffb2e34 into 32e481451 Pull #2839 01 Aug 2026 11:15AM UTC GitHub github
96.96
30697265576 fix/path-param-encoding Tag path params as UTF-8 instead of leaving them binary push 01 Aug 2026 11:14AM UTC Eric Proulx github
96.96
30490601901 fix/path-param-encoding Tag path params as UTF-8 instead of leaving them binary Mustermann decodes path captures out of PATH_INFO, which Rack hands over tagged ASCII-8BIT, and nothing re-tagged the result. Query and body params arrive UTF-8 because Rack tags those itsel... Pull #2839 29 Jul 2026 09:00PM UTC ericproulx github
96.96
30490575051 fix/path-param-encoding Tag path params as UTF-8 instead of leaving them binary Mustermann decodes path captures out of PATH_INFO, which Rack hands over tagged ASCII-8BIT, and nothing re-tagged the result. Query and body params arrive UTF-8 because Rack tags those itsel... push 29 Jul 2026 08:59PM UTC ericproulx github
96.96
See All Builds (3445)
  • Repo on GitHub
  • CI Project
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc