(ns auto-ap.views.pages.admin.accounts
  (:require
   [auto-ap.effects.forward :as forward]
   [auto-ap.forms :as forms]
   [auto-ap.shared-views.admin.side-bar :refer [admin-side-bar]]
   [auto-ap.views.components.buttons :as buttons]
   [auto-ap.views.components.layouts
    :refer [appearing-side-bar side-bar-layout]]
   [auto-ap.views.pages.admin.accounts.form :as account-form]
   [auto-ap.views.pages.admin.accounts.side-bar :as side-bar]
   [auto-ap.views.pages.admin.accounts.table :as table]
   [auto-ap.views.pages.data-page :as data-page]
   [auto-ap.views.utils :refer [with-user]]
   [clojure.set :as set]
   [re-frame.core :as re-frame]
   [reagent.core :as reagent]
   [vimsical.re-frame.fx.track :as track]))

(def default-read [:numeric-code :name :location :type :account_set :applicability :invoice-allowance :vendor-allowance :id [:client-overrides [:id :name [:client [:name :id]]]]])



(re-frame/reg-event-fx
 ::params-change
 [with-user]
 (fn [{:keys [user]} [_ params]]
   {:set-uri-params params
    :graphql {:token user
              :owns-state {:single [::data-page/page ::page]}
              :query-obj {:venia/queries [{:query/data [:account_page
                                                        {:sort      (:sort params)
                                                         :start     (:start params 0)
                                                         :per-page  (:per-page params)
                                                         :name-like (:name-like params)
                                                         :numeric-code (some-> params :numeric-code not-empty js/parseInt)}
                                                        [[:accounts default-read]
                                                         :total
                                                         :start
                                                         :end]]
                                           :query/alias :result}]}
              :on-success (fn [result]
                            [::data-page/received ::page
                             (set/rename-keys (:result result)
                                              {:accounts :data})])}}))


(re-frame/reg-event-fx
 ::unmounted
 (fn [_ _]
   {::track/dispose {:id ::params}
    ::forward/dispose [{:id ::updated}]}))

(re-frame/reg-event-fx
 ::mounted
 (fn  [_ _]
   {::track/register {:id ::params
                      :subscription [::data-page/params ::page]
                      :event-fn (fn [params] [::params-change params])}
    ::forward/register [{:id       ::updated
                         :events   #{::account-form/edited}
                         :event-fn (fn [[_ edited-account]]
                                     [::data-page/updated-entity ::page (:upsert-account edited-account)])}]}))

(defn admin-accounts-content []
  [:div
   [:h1.title "Accounts"]
   [:div.is-pulled-right
    [buttons/new-button {:name "Account"
                         :class "is-primary"
                         :event [::account-form/editing
                                 {:account-set "default"}]}]]
   [table/accounts-table {:data-page ::page}]])

(defn admin-accounts-page []
  (reagent/create-class
   {:display-name "accounts-page"
    :component-will-unmount #(re-frame/dispatch [::unmounted])
    :component-did-mount #(re-frame/dispatch [::mounted])
    :reagent-render
    (fn []
      (let [{:keys [active?]} @(re-frame/subscribe [::forms/form ::account-form/form])]
        [side-bar-layout {:side-bar [admin-side-bar {}
                                     [side-bar/accounts-side-bar {:data-page ::page}]]
                          :main [admin-accounts-content]
                          :right-side-bar [appearing-side-bar {:visible? active?} [account-form/form ]]}]))}))
