add search filtering based on foil card inventory amounts
This commit is contained in:
parent
5fe5568e2a
commit
2e0644057e
|
@ -0,0 +1,5 @@
|
||||||
|
DROP TRIGGER IF EXISTS cards_update_owned_foil_count_trigger ON collection;
|
||||||
|
|
||||||
|
DROP FUNCTION IF EXISTS update_card_owned_foil_count();
|
||||||
|
|
||||||
|
ALTER TABLE cards DROP COLUMN IF EXISTS owned_foil_count;
|
|
@ -0,0 +1,49 @@
|
||||||
|
ALTER TABLE cards ADD COLUMN owned_foil_count INT NOT NULL DEFAULT 0;
|
||||||
|
|
||||||
|
CREATE INDEX cards_owned_foil_count_idx ON cards (owned_foil_count);
|
||||||
|
|
||||||
|
--
|
||||||
|
-- trigger to run whenever a collection row is added/updated that fills in
|
||||||
|
-- the owned_foil_count column in the corresponding card
|
||||||
|
--
|
||||||
|
|
||||||
|
CREATE OR REPLACE FUNCTION update_card_owned_foil_count()
|
||||||
|
RETURNS TRIGGER
|
||||||
|
AS $update_card_owned_foil_count$
|
||||||
|
DECLARE
|
||||||
|
update_card_id TEXT;
|
||||||
|
BEGIN
|
||||||
|
IF (TG_OP = 'DELETE') THEN
|
||||||
|
update_card_id = OLD.card_id;
|
||||||
|
ELSE
|
||||||
|
update_card_id = NEW.card_id;
|
||||||
|
END IF;
|
||||||
|
|
||||||
|
UPDATE cards
|
||||||
|
SET
|
||||||
|
owned_foil_count = (
|
||||||
|
SELECT COALESCE(SUM(quantity), 0)
|
||||||
|
FROM collection cl
|
||||||
|
WHERE cl.card_id = update_card_id AND cl.foil = TRUE
|
||||||
|
)
|
||||||
|
WHERE id = update_card_id;
|
||||||
|
RETURN NULL;
|
||||||
|
END;
|
||||||
|
$update_card_owned_foil_count$ LANGUAGE plpgsql;
|
||||||
|
|
||||||
|
CREATE TRIGGER cards_update_owned_foil_count_trigger
|
||||||
|
AFTER INSERT OR UPDATE OR DELETE ON collection
|
||||||
|
FOR EACH ROW EXECUTE PROCEDURE update_card_owned_foil_count();
|
||||||
|
|
||||||
|
|
||||||
|
--
|
||||||
|
-- fill in owned_foil_count in any existing cards
|
||||||
|
--
|
||||||
|
|
||||||
|
UPDATE cards c
|
||||||
|
SET
|
||||||
|
owned_foil_count = (
|
||||||
|
SELECT COALESCE(SUM(quantity), 0)
|
||||||
|
FROM collection cl
|
||||||
|
WHERE cl.card_id = c.id AND cl.foil = TRUE
|
||||||
|
);
|
|
@ -118,21 +118,23 @@
|
||||||
:< "Less Than"})
|
:< "Less Than"})
|
||||||
|
|
||||||
(def search-filter-defs
|
(def search-filter-defs
|
||||||
{:name {:label "Name" :type :text :comparisons [:like :=]}
|
{:name {:label "Name" :type :text :comparisons [:like :=]}
|
||||||
:set-code {:label "Set" :type :text :comparisons [:=] :component set-search-field-element}
|
:set-code {:label "Set" :type :text :comparisons [:=] :component set-search-field-element}
|
||||||
:colors {:label "Colors" :type :checkbox :comparisons [:like :=] :choices ["Black" "Blue" "Green" "Red" "White"] :component checkboxes-search-field-element}
|
:colors {:label "Colors" :type :checkbox :comparisons [:like :=] :choices ["Black" "Blue" "Green" "Red" "White"] :component checkboxes-search-field-element}
|
||||||
:color-identity {:label "Color Identity" :type :checkbox :comparisons [:like :=] :choices [["Black" "B"] ["Blue" "U"] ["Green" "G"] ["Red" "R"] ["White" "W"]] :component checkboxes-search-field-element}
|
:color-identity {:label "Color Identity" :type :checkbox :comparisons [:like :=] :choices [["Black" "B"] ["Blue" "U"] ["Green" "G"] ["Red" "R"] ["White" "W"]] :component checkboxes-search-field-element}
|
||||||
:type {:label "Type" :type :text :comparisons [:like :=]}
|
:type {:label "Type" :type :text :comparisons [:like :=]}
|
||||||
:rarity {:label "Rarity" :type :dropdown :comparisons [:=] :choices ["Basic Land" "Common" "Mythic Rare" "Rare" "Special" "Uncommon"]}
|
:rarity {:label "Rarity" :type :dropdown :comparisons [:=] :choices ["Basic Land" "Common" "Mythic Rare" "Rare" "Special" "Uncommon"]}
|
||||||
:text {:label "Card Text" :type :text :comparisons [:like :=]}
|
:text {:label "Card Text" :type :text :comparisons [:like :=]}
|
||||||
:artist {:label "Artist" :type :text :comparisons [:like :=]}
|
:artist {:label "Artist" :type :text :comparisons [:like :=]}
|
||||||
:number {:label "Card Number" :type :text :comparisons [:=]}
|
:number {:label "Card Number" :type :text :comparisons [:=]}
|
||||||
:power {:label "Power" :type :text :comparisons [:=]}
|
:power {:label "Power" :type :text :comparisons [:=]}
|
||||||
:toughness {:label "Toughness" :type :text :comparisons [:=]}
|
:toughness {:label "Toughness" :type :text :comparisons [:=]}
|
||||||
:owned? {:label "Owned?" :type :boolean :comparisons [:=]}
|
:owned? {:label "Owned?" :type :boolean :comparisons [:=]}
|
||||||
:owned-count {:label "Owned Amount" :type :numeric :comparisons [:= :> :<] :validation-fn valid-integer? :transform-fn js/parseInt}
|
:owned-foil? {:label "Owned Foil?" :type :boolean :comparisons [:=]}
|
||||||
:paper-price {:label "Price (Paper)" :type :numeric :comparisons [:= :> :<] :validation-fn valid-float? :transform-fn js/parseFloat}
|
:owned-count {:label "Owned Amount" :type :numeric :comparisons [:= :> :<] :validation-fn valid-integer? :transform-fn js/parseInt}
|
||||||
:online-price {:label "Price (Online)" :type :numeric :comparisons [:= :> :<] :validation-fn valid-float? :transform-fn js/parseFloat}})
|
:owned-foil-count {:label "Owned Foil Amount" :type :numeric :comparisons [:= :> :<] :validation-fn valid-integer? :transform-fn js/parseInt}
|
||||||
|
:paper-price {:label "Price (Paper)" :type :numeric :comparisons [:= :> :<] :validation-fn valid-float? :transform-fn js/parseFloat}
|
||||||
|
:online-price {:label "Price (Online)" :type :numeric :comparisons [:= :> :<] :validation-fn valid-float? :transform-fn js/parseFloat}})
|
||||||
|
|
||||||
(defn ->search-field-map
|
(defn ->search-field-map
|
||||||
[field & [filter-id]]
|
[field & [filter-id]]
|
||||||
|
|
|
@ -66,7 +66,8 @@
|
||||||
s.online_only,
|
s.online_only,
|
||||||
c.paper_price,
|
c.paper_price,
|
||||||
c.online_price,
|
c.online_price,
|
||||||
c.owned_count
|
c.owned_count,
|
||||||
|
c.owned_foil_count
|
||||||
from cards c
|
from cards c
|
||||||
join sets s on c.set_code = s.code
|
join sets s on c.set_code = s.code
|
||||||
where c.id = ?" id])
|
where c.id = ?" id])
|
||||||
|
@ -137,39 +138,45 @@
|
||||||
:< (compare-fn fields :< value))))
|
:< (compare-fn fields :< value))))
|
||||||
|
|
||||||
(def search-field-where-clauses
|
(def search-field-where-clauses
|
||||||
{:name (text-comparison-fn [:name :normalized_name])
|
{:name (text-comparison-fn [:name :normalized_name])
|
||||||
:set-code (text-comparison-fn [:set_code] true)
|
:set-code (text-comparison-fn [:set_code] true)
|
||||||
:colors (fn [value comparison]
|
:colors (fn [value comparison]
|
||||||
(let [colors (as-> value x
|
(let [colors (as-> value x
|
||||||
(map string/trim x)
|
(map string/trim x)
|
||||||
(map string/capitalize x)
|
(map string/capitalize x)
|
||||||
(sort x))]
|
(sort x))]
|
||||||
(case comparison
|
(case comparison
|
||||||
:= [:= :colors (string/join "," colors)]
|
:= [:= :colors (string/join "," colors)]
|
||||||
:like [:ilike :colors (str "%" (string/join "%" colors) "%")])))
|
:like [:ilike :colors (str "%" (string/join "%" colors) "%")])))
|
||||||
:color-identity (fn [value comparison]
|
:color-identity (fn [value comparison]
|
||||||
(let [colors (as-> value x
|
(let [colors (as-> value x
|
||||||
(map string/trim x)
|
(map string/trim x)
|
||||||
(map string/upper-case x)
|
(map string/upper-case x)
|
||||||
(sort x))]
|
(sort x))]
|
||||||
(case comparison
|
(case comparison
|
||||||
:= [:= :color_identity (string/join "," colors)]
|
:= [:= :color_identity (string/join "," colors)]
|
||||||
:like [:like :color_identity (str "%" (string/join "%" colors) "%")])))
|
:like [:like :color_identity (str "%" (string/join "%" colors) "%")])))
|
||||||
:type (text-comparison-fn [:type])
|
:type (text-comparison-fn [:type])
|
||||||
:rarity (text-comparison-fn [:rarity] true)
|
:rarity (text-comparison-fn [:rarity] true)
|
||||||
:text (text-comparison-fn [:text])
|
:text (text-comparison-fn [:text])
|
||||||
:artist (text-comparison-fn [:artist])
|
:artist (text-comparison-fn [:artist])
|
||||||
:number (text-comparison-fn [:number] true)
|
:number (text-comparison-fn [:number] true)
|
||||||
:power (text-comparison-fn [:power] true)
|
:power (text-comparison-fn [:power] true)
|
||||||
:toughness (text-comparison-fn [:toughness] true)
|
:toughness (text-comparison-fn [:toughness] true)
|
||||||
:owned-count (numeric-comparison-fn [:owned_count])
|
:owned-count (numeric-comparison-fn [:owned_count])
|
||||||
:paper-price (numeric-comparison-fn [:paper_price])
|
:owned-foil-count (numeric-comparison-fn [:owned_foil_count])
|
||||||
:online-price (numeric-comparison-fn [:online_price])
|
:paper-price (numeric-comparison-fn [:paper_price])
|
||||||
:owned? (fn [value comparison]
|
:online-price (numeric-comparison-fn [:online_price])
|
||||||
(assert (= := comparison))
|
:owned? (fn [value comparison]
|
||||||
(case value
|
(assert (= := comparison))
|
||||||
true [:> :owned_count 0]
|
(case value
|
||||||
false [:= :owned_count 0]))})
|
true [:> :owned_count 0]
|
||||||
|
false [:= :owned_count 0]))
|
||||||
|
:owned-foil? (fn [value comparison]
|
||||||
|
(assert (= := comparison))
|
||||||
|
(case value
|
||||||
|
true [:> :owned_foil_count 0]
|
||||||
|
false [:= :owned_foil_count 0]))})
|
||||||
|
|
||||||
(defn- filter->hsql-where-criteria
|
(defn- filter->hsql-where-criteria
|
||||||
[{:keys [field value comparison]}]
|
[{:keys [field value comparison]}]
|
||||||
|
@ -199,7 +206,8 @@
|
||||||
:c.loyalty
|
:c.loyalty
|
||||||
:c.paper_price
|
:c.paper_price
|
||||||
:c.online_price
|
:c.online_price
|
||||||
:c.owned_count]
|
:c.owned_count
|
||||||
|
:c.owned_foil_count]
|
||||||
:from [[:cards :c]]
|
:from [[:cards :c]]
|
||||||
:join [[:sets :s] [:= :c.set_code :s.code]]}
|
:join [[:sets :s] [:= :c.set_code :s.code]]}
|
||||||
(if order-by
|
(if order-by
|
||||||
|
|
Loading…
Reference in a new issue