we-promise/sure · warning · Api::V1::TransferDecisionFiltering::InvalidFilterError
#{key} must be an ISO 8601 date
Error message
#{key} must be an ISO 8601 date What it means
Api::V1::TransferDecisionFiltering (app/controllers/concerns/api/v1/transfer_decision_filtering.rb:86-92) supplies parse_date_param for the transfers and rejected_transfers index actions, filtering on entries.date with start_date/end_date. Dates must pass strict Date.iso8601; failures are converted by invalid_filter! into InvalidFilterError '<key> must be an ISO 8601 date' and rescued to 422 validation_failed in each controller.
Source
Thrown at app/controllers/concerns/api/v1/transfer_decision_filtering.rb:90
.where(entries: { account_id: accessible_account_ids.where(id: account_id) })
.select(:id)
end
def transfer_date_transaction_ids
query = accessible_transactions
query = query.where("entries.date >= ?", parse_date_param(:start_date)) if params[:start_date].present?
query = query.where("entries.date <= ?", parse_date_param(:end_date)) if params[:end_date].present?
query.select(:id)
end
def parse_date_param(key)
Date.iso8601(params[key].to_s)
rescue ArgumentError
invalid_filter!("#{key} must be an ISO 8601 date")
end
def invalid_filter!(message)
raise InvalidFilterError, message
end
end
View on GitHub (pinned to e69894adb9)
Solutions
- Send start_date/end_date as strict YYYY-MM-DD on /transfers and /rejected_transfers
- Use a single date normalization helper across all list endpoints
- Validate with Date.iso8601 client-side to match server strictness
- On 422, check the message for which key failed before retrying
Example fix
# before GET /api/v1/transfers?start_date=Jan 31, 2024 # after GET /api/v1/transfers?start_date=2024-01-31
Defensive patterns
Strategy: validation
Validate before calling
require 'date' %i[start_date end_date].each do |k| next if filters[k].to_s.strip.empty? Date.iso8601(filters[k]) # strict YYYY-MM-DD or raise end
Type guard
def valid_iso_date?(v) = v.to_s.match?(/\A\d{4}-\d{2}-\d{2}\z/) Try / catch
begin
client.get('/api/v1/transfers', filters)
rescue Faraday::UnprocessableEntity => e
# 422 — body message says '<key> must be an ISO 8601 date'
end Prevention
- Feed every date-filtered endpoint the same YYYY-MM-DD output
- Do not pass spreadsheet-formatted dates through unchecked
- Log the failing key from the 422 body to pinpoint the param
When it happens
Trigger: GET /api/v1/transfers?start_date=2024.01.31 or GET /api/v1/rejected_transfers?end_date=12/31/2024 — any date filter on those two endpoints that is not strict YYYY-MM-DD.
Common situations: One shared date-picker component feeding multiple endpoints while only some are strict; dotted or slashed formats from exports; non-padded dates built by hand.
Related errors
AI-assisted analysis of we-promise/sure@e69894adb9 (2026-08-21).
Data as JSON: /api/errors/7788d8ed3f1c9198.
Report an issue: GitHub.