Module: Datadog::AppSec::RouteNormalizer::RouteText Private
- Defined in:
- lib/datadog/appsec/route_normalizer/route_text.rb
Overview
This module is part of a private API. You should avoid using this module if possible, as it may be removed or be changed in the future.
Percent-encodes route text, leaving param templates untouched
Constant Summary collapse
- DISALLOWED_CHARS =
This constant is part of a private API. You should avoid using this constant if possible, as it may be removed or be changed in the future.
%r{[^\w.~/-]}- BYTE_ENCODING_TABLE =
This constant is part of a private API. You should avoid using this constant if possible, as it may be removed or be changed in the future.
Per-byte percent-encoding lookup, indexed by byte value (0-255)
Example:
32 => 20 (space) 33 => 21 (!) 47 => / (passthrough) 65 => A (passthrough)195 => %C3 (UTF-8 lead byte) 169 => %A9 (UTF-8 continuation byte)
Array.new(256) do |byte| char = byte.chr char.match?(DISALLOWED_CHARS) ? -("%%%02X" % byte) : -char end.freeze
- MAX_ENCODED_BYTE_SIZE =
This constant is part of a private API. You should avoid using this constant if possible, as it may be removed or be changed in the future.
Max bytes one input byte expands to as percent-encoded
%XX 3
Class Method Summary collapse
-
.escape(text) ⇒ Object
private
Escapes literal route text into normalized-route form.
Class Method Details
.escape(text) ⇒ Object
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Escapes literal route text into normalized-route form
Example:
a+b => a%2Bb
caf
NOTE: URI::Parser#escape with DISALLOWED_CHARS gives the same output, but the generic gsub/sprintf path is slower and allocates more per request
42 43 44 45 46 47 48 49 50 51 52 53 |
# File 'lib/datadog/appsec/route_normalizer/route_text.rb', line 42 def escape(text) return text unless text.match?(DISALLOWED_CHARS) buffer = String.new(capacity: text.bytesize * MAX_ENCODED_BYTE_SIZE, encoding: Encoding::UTF_8) text.each_byte { |byte| buffer << BYTE_ENCODING_TABLE.fetch(byte) } buffer # NOTE: Defensive only — this can never happen. {String#each_byte} yields # integers in 0-255 and {BYTE_ENCODING_TABLE} has an entry for every one rescue IndexError => e AppSec.telemetry&.report(e, description: "AppSec: Route text byte outside 0-255 escape table") "~invalid~" end |