Adds the ability to do a column per location

This commit is contained in:
2022-04-03 07:46:15 -07:00
parent 72a97532ee
commit 7739c18bc2
3 changed files with 303 additions and 259 deletions

View File

@@ -192,6 +192,9 @@
(throw (ex-info "Please select a client." {:validation-error "Please select a client."}))) (throw (ex-info "Please select a client." {:validation-error "Please select a client."})))
_ (doseq [client-id client-ids] _ (doseq [client-id client-ids]
(assert-can-see-client (:id context) client-id)) (assert-can-see-client (:id context) client-id))
_ (when (and (:include_deltas args)
(:column_per_location args))
(throw (ex-info "Please select one of 'Include deltas' or 'Column per location'" {:validation-error "Please select one of 'Include deltas' or 'Column per location'"})))
all-ledger-entries (->> client-ids all-ledger-entries (->> client-ids
(map (fn [client-id] (map (fn [client-id]
[client-id (full-ledger-for-client client-id)])) [client-id (full-ledger-for-client client-id)]))
@@ -584,14 +587,16 @@
:args {:client_id {:type :id} :args {:client_id {:type :id}
:client_ids {:type '(list :id)} :client_ids {:type '(list :id)}
:periods {:type '(list :date_range)} :periods {:type '(list :date_range)}
:include_deltas {:type 'Boolean}} :include_deltas {:type 'Boolean}
:column_per_location {:type 'Boolean}}
:resolve :get-profit-and-loss} :resolve :get-profit-and-loss}
:profit_and_loss_pdf {:type :report_pdf :profit_and_loss_pdf {:type :report_pdf
:args {:client_id {:type :id} :args {:client_id {:type :id}
:client_ids {:type '(list :id)} :client_ids {:type '(list :id)}
:periods {:type '(list :date_range)} :periods {:type '(list :date_range)}
:include_deltas {:type 'Boolean}} :include_deltas {:type 'Boolean}
:column_per_location {:type 'Boolean}}
:resolve :profit-and-loss-pdf} :resolve :profit-and-loss-pdf}
:balance_sheet_pdf {:type :report_pdf :balance_sheet_pdf {:type :report_pdf

View File

@@ -90,9 +90,11 @@
(vals ranges)) (vals ranges))
false)) false))
(defn locations [data] (defn client-locations [pnl-data]
(->> data (->> pnl-data
:data
(filter (comp in-range? :numeric-code)) (filter (comp in-range? :numeric-code))
(filter #(not= "A" (:location %)))
(group-by (juxt :client-id :location)) (group-by (juxt :client-id :location))
(filter (fn [[_ as]] (filter (fn [[_ as]]
(not (dollars-0? (reduce + 0 (map :amount as)))))) (not (dollars-0? (reduce + 0 (map :amount as))))))
@@ -112,6 +114,15 @@
"ZZZZZZ" "ZZZZZZ"
(:location x))])))) (:location x))]))))
(defn locations [pnl-data]
(->> (client-locations pnl-data)
(map second)
set
(sort-by (fn [x]
(if (= x "HQ" )
"ZZZZZZ"
x)))))
(defn aggregate-accounts [pnl-data] (defn aggregate-accounts [pnl-data]
(reduce (fnil + 0.0) 0.0 (map :amount (:data pnl-data)))) (reduce (fnil + 0.0) 0.0 (map :amount (:data pnl-data))))
@@ -179,34 +190,32 @@
accounts)))) accounts))))
(defn used-accounts [pnl-data] (defn used-accounts [pnl-datas]
(->> (:data pnl-data) (->>
pnl-datas
(mapcat :data)
(map #(select-keys % [:numeric-code :name])) (map #(select-keys % [:numeric-code :name]))
(set) (set)
(sort-by :numeric-code))) (sort-by :numeric-code)))
(defn subtotal-row [pnl-data title & [cell-args]] (defn subtotal-by-column-row [pnl-datas title & [cell-args]]
(into [{:value title (into [{:value title
:bold true :bold true}]
:filters (when (:from-numeric-code (:filters pnl-data)) ;; don't allow filtering when you don't at least filter numeric codes
(:filters pnl-data))}]
(map (map
(fn [p] (fn [p]
(let [data (filter-period pnl-data p)]
(merge (merge
{:format :dollar {:format :dollar
:value (aggregate-accounts data) :value (aggregate-accounts p)
:filters (when (:from-numeric-code (:filters data)) ;; don't allow filtering when you don't at least filter numeric codes :filters (when (:from-numeric-code (:filters p)) ;; don't allow filtering when you don't at least filter numeric codes
(:filters data))} (:filters p))}
cell-args))) cell-args))
(-> pnl-data :args :periods)))) pnl-datas)))
(defn calc-percent-of-sales [table pnl-data] (defn calc-percent-of-sales [table pnl-datas]
(let [sales-pnl-data (filter-categories pnl-data [:sales]) (let [sales (map
sales (map
(fn [p] (fn [p]
(aggregate-accounts (filter-period sales-pnl-data p))) (aggregate-accounts (filter-categories p [:sales])))
(-> pnl-data :args :periods))] pnl-datas)]
(->> table (->> table
(map (fn [[_ & values]] (map (fn [[_ & values]]
(map (map
@@ -231,7 +240,7 @@
(:value a))}))))))) (:value a))})))))))
(defn combine-tables (defn combine-tables
([pnl-data table percent-of-sales deltas] ([[pnl-data] table percent-of-sales deltas]
(map (fn [[title & row] percent-of-sales deltas ] (map (fn [[title & row] percent-of-sales deltas ]
(let [deltas (cons {:value 0.0 (let [deltas (cons {:value 0.0
:format :dollar :format :dollar
@@ -249,21 +258,39 @@
percent-of-sales percent-of-sales
deltas))) deltas)))
(defn headers [pnl-data header-title] (defn headers [[pnl-data :as pnl-datas] header-title]
(let [big-header (into [{:value header-title (let [
big-header (into [{:value header-title
:bold true}] :bold true}]
(map (fn [p] (map (fn [p]
{:value {:value
(str (date->str (:start p)) (str (date->str (:start p))
" - " " - "
(date->str (:end p))) (date->str (:end p)))
:colspan (if (-> pnl-data :args :include-deltas) :colspan (cond
(-> pnl-data :args :include-deltas)
3 3
(-> pnl-data :args :column-per-location)
(* 2 (/ (count pnl-datas)
(count (-> pnl-data :args :periods))))
:else
2) 2)
:align :center :align :center
:bold true}) :bold true})
(:periods (:args pnl-data)))) (:periods (:args pnl-data))))
sub-header (into [{:value ""}] sub-header (into [{:value ""}]
(if (-> pnl-data :args :column-per-location)
(mapcat
(fn [p]
(cond-> [{:value (-> p :filters :location)
:align :right}
{:value "%"
:align :right}]
(-> pnl-data :args :include-deltas) (conj {:value "+/-"
:align :right})))
pnl-datas)
(mapcat (mapcat
(fn [_] (fn [_]
(cond-> [{:value "Amt" (cond-> [{:value "Amt"
@@ -272,107 +299,115 @@
:align :right}] :align :right}]
(-> pnl-data :args :include-deltas) (conj {:value "+/-" (-> pnl-data :args :include-deltas) (conj {:value "+/-"
:align :right}))) :align :right})))
(:periods (:args pnl-data))))] pnl-datas)))]
[big-header [big-header
sub-header])) sub-header]))
(defn location-summary-table [pnl-data title] (defn location-summary-table [pnl-datas title]
(let [table [(subtotal-row (filter-categories pnl-data [:sales]) "Sales") (let [table [(subtotal-by-column-row (map #(filter-categories % [:sales])
(subtotal-row (filter-categories pnl-data [:cogs ]) "Cogs") pnl-datas)
"Sales")
(subtotal-by-column-row (map #(filter-categories % [:cogs ]) pnl-datas)
"Cogs")
(subtotal-row (filter-categories pnl-data [:payroll ]) "Payroll") (subtotal-by-column-row (map #(filter-categories % [:payroll ]) pnl-datas)
"Payroll")
(subtotal-row (-> pnl-data (subtotal-by-column-row (map #(-> %
(filter-categories [:sales :payroll :cogs]) (filter-categories [:sales :payroll :cogs])
(negate #{:payroll :cogs})) (negate #{:payroll :cogs}))
pnl-datas)
"Gross Profits") "Gross Profits")
(subtotal-row (filter-categories pnl-data [:controllable :fixed-overhead :ownership-controllable]) (subtotal-by-column-row (map #(filter-categories % [:controllable :fixed-overhead :ownership-controllable])
pnl-datas)
"Overhead") "Overhead")
(subtotal-row (-> pnl-data (subtotal-by-column-row (map #(-> %
(filter-categories [:sales :cogs :payroll :controllable :fixed-overhead :ownership-controllable]) (filter-categories [:sales :cogs :payroll :controllable :fixed-overhead :ownership-controllable])
(negate #{:cogs :payroll :controllable :fixed-overhead :ownership-controllable})) (negate #{:cogs :payroll :controllable :fixed-overhead :ownership-controllable}))
pnl-datas)
"Net Income")] "Net Income")]
percent-of-sales (calc-percent-of-sales table pnl-data) percent-of-sales (calc-percent-of-sales table pnl-datas)
deltas (calc-deltas table)] deltas (calc-deltas table)]
{:header (headers pnl-data title) {:header (headers pnl-datas title)
:rows (combine-tables pnl-data table percent-of-sales deltas)})) :rows (combine-tables pnl-datas table percent-of-sales deltas)}))
(defn detail-rows [pnl-data grouping title] (defn detail-rows [pnl-datas grouping title]
(let [pnl-data (filter-categories pnl-data [grouping]) (let [pnl-datas (map #(filter-categories % [grouping])
pnl-datas)
individual-accounts individual-accounts
(for [[grouping-name from to] (groupings grouping) (for [[grouping-name from to] (groupings grouping)
:let [pnl-data (filter-numeric-code pnl-data from to) :let [pnl-datas (map #(filter-numeric-code % from to)
account-codes (used-accounts pnl-data)] pnl-datas)
account-codes (used-accounts pnl-datas)]
:when (seq account-codes) :when (seq account-codes)
row (-> [[{:value (str "---" grouping-name "---")}]] row (-> [[{:value (str "---" grouping-name "---")}]]
(into (for [{:keys [numeric-code name]} account-codes] (into (for [{:keys [numeric-code name]} account-codes]
(into [{:value name}] (into [{:value name}]
(map (map
(fn [p] (fn [p]
(let [pnl-data (-> pnl-data (let [pnl-data (-> p (filter-numeric-code numeric-code numeric-code))]
(filter-numeric-code numeric-code numeric-code)
(filter-period p)
)]
{:format :dollar {:format :dollar
:filters (:filters pnl-data) :filters (:filters pnl-data)
:value (aggregate-accounts pnl-data)})) :value (aggregate-accounts pnl-data)}))
(-> pnl-data :args :periods))))) pnl-datas))))
(conj (subtotal-row pnl-data "" {:border [:top]})))] (conj (subtotal-by-column-row pnl-datas "" {:border [:top]})))]
row)] row)]
(-> [[{:value title (-> [[{:value title
:bold true}]] :bold true}]]
(into individual-accounts) (into individual-accounts)
(conj (subtotal-row pnl-data title))))) (conj (subtotal-by-column-row pnl-datas title)))))
(defn location-detail-table [pnl-data client-data title] (defn location-detail-table [pnl-datas client-data title prefix]
(let [table (-> [] (let [table (-> []
(into (detail-rows pnl-data (into (detail-rows pnl-datas
:sales :sales
(str (:prefix pnl-data) " Sales"))) (str prefix " Sales")))
(into (detail-rows pnl-data (into (detail-rows pnl-datas
:cogs :cogs
(str (:prefix pnl-data) " COGS"))) (str prefix " COGS")))
(into (detail-rows (into (detail-rows
pnl-data pnl-datas
:payroll :payroll
(str (:prefix pnl-data) " Payroll"))) (str prefix " Payroll")))
(conj (subtotal-row (filter-categories pnl-data [:payroll :cogs]) (conj (subtotal-by-column-row (map #(filter-categories % [:payroll :cogs])
(str (:prefix pnl-data) " Prime Costs"))) pnl-datas)
(conj (subtotal-row (-> pnl-data (str prefix " Prime Costs")))
(conj (subtotal-by-column-row (map #(-> %
(filter-categories [:sales :payroll :cogs]) (filter-categories [:sales :payroll :cogs])
(negate #{:payroll :cogs})) (negate #{:payroll :cogs}))
(str (:prefix pnl-data) " Gross Profits"))) pnl-datas)
(str prefix " Gross Profits")))
(into (detail-rows (into (detail-rows
pnl-data pnl-datas
:controllable :controllable
(str (:prefix pnl-data) " Controllable Expenses"))) (str prefix " Controllable Expenses")))
(into (detail-rows (into (detail-rows
pnl-data pnl-datas
:fixed-overhead :fixed-overhead
(str (:prefix pnl-data) " Fixed Overhead"))) (str prefix " Fixed Overhead")))
(into (detail-rows (into (detail-rows
pnl-data pnl-datas
:ownership-controllable :ownership-controllable
(str (:prefix pnl-data) " Ownership Controllable"))) (str prefix " Ownership Controllable")))
(conj (subtotal-row (-> pnl-data (conj (subtotal-by-column-row (map #(filter-categories % [:controllable :fixed-overhead :ownership-controllable]) pnl-datas)
(filter-categories [:controllable :fixed-overhead :ownership-controllable])) (str prefix " Overhead")))
(str (:prefix pnl-data) " Overhead"))) (conj (subtotal-by-column-row (map #(-> %
(conj (subtotal-row (-> pnl-data
(filter-categories [:sales :cogs :payroll :controllable :fixed-overhead :ownership-controllable]) (filter-categories [:sales :cogs :payroll :controllable :fixed-overhead :ownership-controllable])
(negate #{:cogs :payroll :controllable :fixed-overhead :ownership-controllable})) (negate #{:cogs :payroll :controllable :fixed-overhead :ownership-controllable}))
(str (:prefix pnl-data) " Net Income"))) pnl-datas)
(conj (subtotal-row (-> client-data (str prefix " Net Income")))
(conj (subtotal-by-column-row (-> client-data
(filter-categories [:sales :cogs :payroll :controllable :fixed-overhead :ownership-controllable]) (filter-categories [:sales :cogs :payroll :controllable :fixed-overhead :ownership-controllable])
(negate #{:cogs :payroll :controllable :fixed-overhead :ownership-controllable})) (negate #{:cogs :payroll :controllable :fixed-overhead :ownership-controllable}))
"All Location Net Income"))) "All Location Net Income")))
percent-of-sales (calc-percent-of-sales table pnl-data) percent-of-sales (calc-percent-of-sales table pnl-datas)
deltas (into [] (calc-deltas table))] deltas (into [] (calc-deltas table))]
{:header (headers pnl-data title) {:header (headers pnl-datas title)
:rows (combine-tables pnl-data table percent-of-sales deltas)})) :rows (combine-tables pnl-datas table percent-of-sales deltas)}))
(defn warning-message [pnl-data] (defn warning-message [pnl-data]
(let [errors (->> pnl-data (let [errors (->> pnl-data
@@ -390,19 +425,47 @@
(defn summarize-pnl [pnl-data] (defn summarize-pnl [pnl-data]
{:warning (warning-message pnl-data) {:warning (warning-message pnl-data)
:summaries (for [[client-id location] (locations (:data pnl-data))] :summaries
(location-summary-table (-> pnl-data (if (-> pnl-data :args :column-per-location)
(filter-client client-id) (for [client-id (set (map first (client-locations pnl-data)))]
(filter-location location)) (location-summary-table (for [period (-> pnl-data :args :periods )
(str (-> pnl-data :clients-by-id (get client-id)) " (" location ") Summary"))) location (locations pnl-data)]
:details (for [[client-id location] (locations (:data pnl-data))] (-> pnl-data
(location-detail-table (-> pnl-data
(filter-client client-id) (filter-client client-id)
(filter-location location) (filter-location location)
(assoc :prefix location)) (filter-period period)))
(str (-> pnl-data :clients-by-id (get client-id)) " Summary")))
(for [[client-id location] (client-locations pnl-data)]
(location-summary-table (for [period (-> pnl-data :args :periods )]
(-> pnl-data
(filter-client client-id)
(filter-location location)
(filter-period period)))
(str (-> pnl-data :clients-by-id (get client-id)) " (" location ") Summary"))))
:details
(doall (if (-> pnl-data :args :column-per-location)
(for [client-id (set (map first (client-locations pnl-data)))]
(location-detail-table (for [period (-> pnl-data :args :periods )
location (locations pnl-data)]
(-> pnl-data
(filter-client client-id)
(filter-location location)
(filter-period period)))
(-> pnl-data (-> pnl-data
(filter-client client-id)) (filter-client client-id))
(str (-> pnl-data :clients-by-id (get client-id)) " (" location ") Detail")))}) (str (-> pnl-data :clients-by-id (get client-id)) " Detail")
""))
(for [[client-id location] (client-locations pnl-data)]
(location-detail-table (for [period (-> pnl-data :args :periods )]
(-> pnl-data
(filter-client client-id)
(filter-location location)
(filter-period period)))
(-> pnl-data
(filter-client client-id))
(str (-> pnl-data :clients-by-id (get client-id)) " (" location ") Detail")
location))))
})
(defn balance-sheet-headers [pnl-data] (defn balance-sheet-headers [pnl-data]
@@ -420,19 +483,26 @@
(:value b))})])))) (:value b))})]))))
(defn summarize-balance-sheet [pnl-data] (defn summarize-balance-sheet [pnl-data]
(let [table (-> [] (let [
(into (detail-rows pnl-data pnl-datas (map (fn [p]
(filter-period pnl-data p))
(:periods (:args pnl-data)))
table (-> []
(into (detail-rows pnl-datas
:assets :assets
"Assets")) "Assets"))
(into (detail-rows pnl-data (into (detail-rows pnl-datas
:liabilities :liabilities
"Liabilities")) "Liabilities"))
(into (detail-rows pnl-data (into (detail-rows pnl-datas
:equities :equities
"Owner's Equity")) "Owner's Equity"))
(conj (subtotal-row (-> pnl-data (conj (subtotal-by-column-row
(map #(-> %
(filter-categories [:sales :cogs :payroll :controllable :fixed-overhead :ownership-controllable]) (filter-categories [:sales :cogs :payroll :controllable :fixed-overhead :ownership-controllable])
(negate #{:cogs :payroll :controllable :fixed-overhead :ownership-controllable})) (negate #{:cogs :payroll :controllable :fixed-overhead :ownership-controllable}))
pnl-datas)
"Retained Earnings"))) "Retained Earnings")))
table (if (:include-comparison (:args pnl-data)) table (if (:include-comparison (:args pnl-data))
(append-deltas table) (append-deltas table)

View File

@@ -73,7 +73,9 @@
:owns-state {:single ::page} :owns-state {:single ::page}
:query-obj {:venia/queries [[:profit-and-loss :query-obj {:venia/queries [[:profit-and-loss
{:client-ids (map :id (:clients (:data db))) {:client-ids (map :id (:clients (:data db)))
:periods (mapv encode-period (:periods (:data db)))} :periods (mapv encode-period (:periods (:data db)))
:include-deltas (:include-deltas (:data db))
:column-per-location (:column-per-location (:data db))}
[[:periods [[:accounts [:name :amount :client_id :account-type :id :count :numeric-code :location]]]]]]]} [[:periods [[:accounts [:name :amount :client_id :account-type :id :count :numeric-code :location]]]]]]]}
:on-success [::received]} :on-success [::received]}
:set-uri-params {:periods (mapv :set-uri-params {:periods (mapv
@@ -124,6 +126,7 @@ NOTE: Please review the transactions we may have question for you here: https://
:query-obj {:venia/queries [[:profit-and-loss-pdf :query-obj {:venia/queries [[:profit-and-loss-pdf
{:client-ids (map :id (:clients (:data db))) {:client-ids (map :id (:clients (:data db)))
:include-deltas (:include-deltas (:data db)) :include-deltas (:include-deltas (:data db))
:column-per-location (:column-per-location (:data db))
:periods (mapv encode-period (:periods (:data db)))} :periods (mapv encode-period (:periods (:data db)))}
[:url :name]]]} [:url :name]]]}
:on-success [::received-pdf]} :on-success [::received-pdf]}
@@ -144,7 +147,7 @@ NOTE: Please review the transactions we may have question for you here: https://
(= 2 (count field))) (= 2 (count field)))
[field value] ;;already serialized [field value] ;;already serialized
(= :periods (first field)) [field (str->date value standard) ] (= :periods (first field)) [field value ]
:else nil) :else nil)
))) )))
@@ -233,13 +236,25 @@ NOTE: Please review the transactions we may have question for you here: https://
]) ])
@box))) @box)))
(defn period-preset-button [{:keys [title periods]}]
(let [{{:keys [selected-preset]} :data} @(re-frame/subscribe [::forms/form ::form])]
[:div.control
[:a.button
{:class (when (= selected-preset title) "is-active")
:on-click (dispatch-event
[::change
[:periods]
periods
[:selected-preset] title])}
title]]))
(defn report-controls [_] (defn report-controls [_]
(let [!box (reagent/atom nil) (let [!box (reagent/atom nil)
active (reagent/atom nil)] active (reagent/atom nil)]
(fn [pnl-form] (fn [pnl-form]
(let [{:keys [raw-field]} pnl-form (let [{:keys [raw-field]} pnl-form
{:keys [data]} @(re-frame/subscribe [::forms/form ::form]) {:keys [data]} @(re-frame/subscribe [::forms/form ::form])
{:keys [periods selected-period include-deltas]} data] {:keys [periods selected-preset include-deltas column-per-location]} data]
[:div.report-controls [:div.report-controls
[:div.level.mb-2 [:div.level.mb-2
[:div.level-left [:div.level-left
@@ -261,8 +276,8 @@ NOTE: Please review the transactions we may have question for you here: https://
[:div.level-item [:div.level-item
[buttons/dropdown {:on-click (fn [] (reset! active :range))} [buttons/dropdown {:on-click (fn [] (reset! active :range))}
[:span (str "Range" [:span (str "Range"
(when selected-period (when selected-preset
(str " (" selected-period ")")))]] (str " (" selected-preset ")")))]]
[report-control-detail {:active active :box !box :which :range} [report-control-detail {:active active :box !box :which :range}
[:div [:div
[:h4.subtitle "Range"] [:h4.subtitle "Range"]
@@ -273,14 +288,10 @@ NOTE: Please review the transactions we may have question for you here: https://
(raw-field (raw-field
[date-picker-friendly {:placeholder "End date" [date-picker-friendly {:placeholder "End date"
:type "date" :type "date"
:cljs-date? true
:field [:thirteen-periods-end]}])] :field [:thirteen-periods-end]}])]
[:div.control [period-preset-button {:title "13 periods"
[:a.button :periods (let [today (or (some-> (:thirteen-periods-end data))
{:class (when (= selected-period "13 periods") "is-active")
:on-click (dispatch-event
[::change
[:periods]
(let [today (or (some-> (:thirteen-periods-end data) (str->date standard))
(local-today))] (local-today))]
(into (into
[{:start (t/plus (t/minus today (t/weeks (* 13 4))) [{:start (t/plus (t/minus today (t/weeks (* 13 4)))
@@ -290,24 +301,18 @@ NOTE: Please review the transactions we may have question for you here: https://
(for [i (range 13)] (for [i (range 13)]
{:start (t/plus (t/minus today (t/weeks (* (inc i) 4))) {:start (t/plus (t/minus today (t/weeks (* (inc i) 4)))
(t/days 1)) (t/days 1))
:end (t/minus today (t/weeks (* i 4)))}))) :end (t/minus today (t/weeks (* i 4)))})))}]]]
[:selected-period] "13 periods"])}
"13 periods"]]]]
[:div.control [:div.control
[:div.field.has-addons [:div.field.has-addons
[:div.control [:div.control
(raw-field (raw-field
[date-picker-friendly {:placeholder "End date" [date-picker-friendly {:placeholder "End date"
:cljs-date? true
:type "date" :type "date"
:field [:twelve-periods-end]}])] :field [:twelve-periods-end]}])]
[:div.control [period-preset-button {:title "12 months"
[:a.button :periods (let [end-date (or (some-> (:twelve-periods-end data))
{:class (when (= selected-period "12 months") "is-active")
:on-click (dispatch-event
[::change
[:periods]
(let [end-date (or (some-> (:twelve-periods-end data) (str->date standard))
(local-today)) (local-today))
this-month (t/local-date (t/year end-date) this-month (t/local-date (t/year end-date)
(t/month end-date) (t/month end-date)
@@ -320,45 +325,24 @@ NOTE: Please review the transactions we may have question for you here: https://
(for [i (range 12)] (for [i (range 12)]
{:start (t/minus this-month (t/months (- 11 i))) {:start (t/minus this-month (t/months (- 11 i)))
:end (t/minus (t/minus this-month (t/months (- 10 i))) :end (t/minus (t/minus this-month (t/months (- 10 i)))
(t/days 1))}))) (t/days 1))})))}]]]
[:selected-period] "12 months"])}
"12 months"]]]]
[:div.control [period-preset-button {:periods (let [last-sunday (loop [current (local-today)]
[:a.button
{:class (when (= selected-period "Last week") "is-active")
:on-click (dispatch-event
[::change
[:periods]
(let [last-sunday (loop [current (local-today)]
(if (= 7 (t/day-of-week current)) (if (= 7 (t/day-of-week current))
current current
(recur (t/minus current (t/period :days 1)))))] (recur (t/minus current (t/period :days 1)))))]
(and-last-year {:start (t/minus last-sunday (t/period :days 6)) (and-last-year {:start (t/minus last-sunday (t/period :days 6))
:end last-sunday})) :end last-sunday}))
[:selected-period] "Last week"])} :title "Last week"}]
"Last week"]]
[:div.control [period-preset-button {:periods (and-last-year {:start (loop [current (local-today)]
[:a.button
{:class (when (= selected-period "Week to date") "is-active")
:on-click (dispatch-event
[::change
[:periods]
(and-last-year {:start (loop [current (local-today)]
(if (= 1 (t/day-of-week current)) (if (= 1 (t/day-of-week current))
current current
(recur (t/minus current (t/period :days 1))))) (recur (t/minus current (t/period :days 1)))))
:end (local-today)}) :end (local-today)})
[:selected-period] "Week to date"])} :title "Week to date"}]
"Week to date"]]
[:div.control
[:a.button
{:class (when (= selected-period "Last Month") "is-active")
:on-click (dispatch-event
[::change [period-preset-button {:periods (and-last-year {:start (t/minus (t/local-date (t/year (local-today))
[:periods]
(and-last-year {:start (t/minus (t/local-date (t/year (local-today))
(t/month (local-today)) (t/month (local-today))
1) 1)
(t/period :months 1)) (t/period :months 1))
@@ -366,53 +350,27 @@ NOTE: Please review the transactions we may have question for you here: https://
(t/month (local-today)) (t/month (local-today))
1) 1)
(t/period :days 1))}) (t/period :days 1))})
[:selected-period] "Last Month"])} :title "Last month"}]
"Last Month"]]
[:div.control [period-preset-button {:periods (and-last-year {:start (t/local-date (t/year (local-today))
[:a.button
{:class (when (= selected-period "Month to date") "is-active")
:on-click (dispatch-event
[::change
[:periods]
(and-last-year {:start (t/local-date (t/year (local-today))
(t/month (local-today)) (t/month (local-today))
1) 1)
:end (local-today)}) :end (local-today)})
[:selected-period] "Month to date"] :title "Month to date"}]
)}
"Month to date"]] [period-preset-button {:periods (and-last-year {:start (t/local-date (t/year (local-today)) 1 1)
[:div.control
[:a.button
{:class (when (= selected-period "Year to date") "is-active")
:on-click (dispatch-event
[::change
[:periods]
(and-last-year {:start (t/local-date (t/year (local-today)) 1 1)
:end :end
(local-today)}) (local-today)})
[:selected-period] "Year to date"])} :title "Year to date"}]
"Year to date"]]
[:div.control [period-preset-button {:periods [{:start (t/local-date (dec (t/year (local-today))) 1 1)
[:a.button
{:class (when (= selected-period "Full year") "is-active")
:on-click (dispatch-event
[::change
[:periods]
[{:start (t/local-date (dec (t/year (local-today))) 1 1)
:end (t/local-date (dec (t/year (local-today))) 12 31)}] :end (t/local-date (dec (t/year (local-today))) 12 31)}]
[:selected-period] "Last Calendar year"])} :title "Last calendar year"}]
"Last calendar year"]]
[:div.control [period-preset-button {:periods (and-last-year {:start (t/plus (t/minus (local-today) (t/period :years 1))
[:a.button
{:class (when (= selected-period "Full year") "is-active")
:on-click (dispatch-event
[::change
[:periods]
(and-last-year {:start (t/plus (t/minus (local-today) (t/period :years 1))
(t/period :days 1)) (t/period :days 1))
:end (local-today)}) :end (local-today)})
[:selected-period] "Full year"])} :title "Full year"}]]
"Full year"]]]
[:div [:div
[:div.field [:div.field
[:label.checkbox [:label.checkbox
@@ -429,12 +387,14 @@ NOTE: Please review the transactions we may have question for you here: https://
[:p.help "From"] [:p.help "From"]
(raw-field (raw-field
[date-picker-friendly {:type "date" [date-picker-friendly {:type "date"
:cljs-date? true
:field [:periods i :start]}])] :field [:periods i :start]}])]
[:div.control [:div.control
[:p.help "To"] [:p.help "To"]
(raw-field (raw-field
[date-picker-friendly {:type "date" [date-picker-friendly {:type "date"
:cljs-date? true
:field [:periods i :end]}])]])))]]] :field [:periods i :end]}])]])))]]]
[:div.level-item [:div.level-item
@@ -445,6 +405,15 @@ NOTE: Please review the transactions we may have question for you here: https://
(re-frame/dispatch [::change (re-frame/dispatch [::change
[:include-deltas] (.-checked (.-target e))])) [:include-deltas] (.-checked (.-target e))]))
:label "Include deltas" :label "Include deltas"
:type "checkbox"}]]]
[:div.level-item
[:div
[switch-field {:id "column-per-location"
:checked (boolean column-per-location)
:on-change (fn [e]
(re-frame/dispatch [::change
[:column-per-location] (.-checked (.-target e))]))
:label "Column per location"
:type "checkbox"}]]]] :type "checkbox"}]]]]
[:div.level-right [:div.level-right
[:div.buttons [:div.buttons