- Add subsonic boolean field to products with composite filter indexes - Add TextDetector utility for detecting subsonic/casing from product titles - Wire TextDetector into SgAmmo (casing + subsonic) and LuckyGunner (subsonic + fallback casing) - Extend latest_prices_for_caliber with casing, grain_weight, and subsonic filter options - Add distinct_grain_weights_for_caliber and distinct_casings_for_caliber queries - Add filter UI with toggleable casing, grain weight, and subsonic buttons - Add grain weight column and subsonic badge to product table - Refresh filter options on PubSub price updates for real-time UI - Implement Target Sports USA scraper with 18 caliber mappings - Display all prices in dollar format ($0.38 instead of 38¢)
20 lines
557 B
Elixir
20 lines
557 B
Elixir
defmodule Ammoprices.Scraping.TextDetector do
|
|
@moduledoc false
|
|
|
|
def detect_subsonic(nil), do: false
|
|
def detect_subsonic(title), do: Regex.match?(~r/sub[\-\s]?sonic/i, title)
|
|
|
|
def detect_casing(nil), do: nil
|
|
|
|
def detect_casing(title) do
|
|
downcased = String.downcase(title)
|
|
|
|
cond do
|
|
String.contains?(downcased, "steel") -> "steel"
|
|
String.contains?(downcased, "aluminum") -> "aluminum"
|
|
String.contains?(downcased, "nickel") -> "brass"
|
|
String.contains?(downcased, "brass") -> "brass"
|
|
true -> nil
|
|
end
|
|
end
|
|
end
|