Skip to content

Commit 32840bc

Browse files
committed
Enhance timestamp parsing: add detailed documentation for ISO 8601 and Unix timestamp methods
1 parent f057fdd commit 32840bc

File tree

1 file changed

+25
-2
lines changed

1 file changed

+25
-2
lines changed

lib/hooks/plugins/auth/hmac.rb

Lines changed: 25 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -209,6 +209,11 @@ def self.valid_timestamp?(headers, config)
209209
end
210210

211211
# Parse timestamp value supporting both ISO 8601 UTC and Unix formats
212+
#
213+
# @param timestamp_value [String] The timestamp string to parse
214+
# @return [Integer, nil] Epoch seconds if parsing succeeds, nil otherwise
215+
# @note Security: Strict validation prevents various injection attacks
216+
# @api private
212217
def self.parse_timestamp(timestamp_value)
213218
# Reject if contains any control characters, whitespace, or null bytes
214219
if timestamp_value =~ /[\u0000-\u001F\u007F-\u009F]/
@@ -230,11 +235,20 @@ def self.parse_timestamp(timestamp_value)
230235
end
231236

232237
# Check if timestamp string looks like ISO 8601 UTC format (must have UTC indicator)
238+
#
239+
# @param timestamp_value [String] The timestamp string to check
240+
# @return [Boolean] true if it appears to be ISO 8601 format (with or without UTC indicator)
241+
# @api private
233242
def self.iso8601_timestamp?(timestamp_value)
234243
!!(timestamp_value =~ /\A\d{4}-\d{2}-\d{2}[T ]\d{2}:\d{2}:\d{2}(?:\.\d+)?(Z|\+00:00|\+0000)?\z/)
235244
end
236245

237246
# Parse ISO 8601 UTC timestamp string (must have UTC indicator)
247+
#
248+
# @param timestamp_value [String] ISO 8601 timestamp string
249+
# @return [Integer, nil] Epoch seconds if parsing succeeds, nil otherwise
250+
# @note Only accepts UTC timestamps (ending with 'Z', '+00:00', '+0000')
251+
# @api private
238252
def self.parse_iso8601_timestamp(timestamp_value)
239253
if timestamp_value =~ /\A(\d{4}-\d{2}-\d{2}) (\d{2}:\d{2}:\d{2}(?:\.\d+)?)(?: )\+0000\z/
240254
timestamp_value = "#{$1}T#{$2}+00:00"
@@ -246,6 +260,11 @@ def self.parse_iso8601_timestamp(timestamp_value)
246260
end
247261

248262
# Parse Unix timestamp string (must be positive integer, no leading zeros except for "0")
263+
#
264+
# @param timestamp_value [String] Unix timestamp string
265+
# @return [Integer, nil] Epoch seconds if parsing succeeds, nil otherwise
266+
# @note Only accepts positive integer values, no leading zeros except for "0"
267+
# @api private
249268
def self.parse_unix_timestamp(timestamp_value)
250269
return nil unless unix_timestamp?(timestamp_value)
251270
ts = timestamp_value.to_i
@@ -254,6 +273,10 @@ def self.parse_unix_timestamp(timestamp_value)
254273
end
255274

256275
# Check if timestamp string looks like Unix timestamp format (no leading zeros except "0")
276+
#
277+
# @param timestamp_value [String] The timestamp string to check
278+
# @return [Boolean] true if it appears to be Unix timestamp format
279+
# @api private
257280
def self.unix_timestamp?(timestamp_value)
258281
return true if timestamp_value == "0"
259282
!!(timestamp_value =~ /\A[1-9]\d*\z/)
@@ -306,7 +329,7 @@ def self.compute_signature(payload:, headers:, secret:, config:)
306329
# - {body}: Replaced with the raw payload
307330
# @example Template usage
308331
# template: "{version}:{timestamp}:{body}"
309-
# result: "v0:1609459200:{"event":"push"}"
332+
# result: "v0:1609459200:{\"event\":\"push\"}"
310333
# @api private
311334
def self.build_signing_payload(payload:, headers:, config:)
312335
template = config[:payload_template]
@@ -336,7 +359,7 @@ def self.build_signing_payload(payload:, headers:, config:)
336359
# - :algorithm_prefixed: "sha256=abc123..." (GitHub style)
337360
# - :hash_only: "abc123..." (Shopify style)
338361
# - :version_prefixed: "v0=abc123..." (Slack style)
339-
# @note Defaults to algorithm_prefixed format for unknown format styles
362+
# @note Defaults to algorithm-prefixed format for unknown format styles
340363
# @api private
341364
def self.format_signature(hash, config)
342365
format_style = FORMATS[config[:format]]

0 commit comments

Comments
 (0)