(ns auto-ap.graphql.accounts
  (:require [datomic.api :as d]
            [auto-ap.datomic.accounts :as d-accounts]
            [auto-ap.graphql.utils :refer [->graphql <-graphql enum->keyword] ]
            [auto-ap.datomic :refer [uri merge-query remove-nils audit-transact]]
            [clojure.tools.logging :as log]))



(defn get-accounts [context args value]
  (->graphql (d-accounts/get-accounts (<-graphql args))))

(defn upsert-account [context args value]
  (let [{{:keys [id client-overrides numeric-code location applicability account-set name type]} :account} (<-graphql args)]
    (when-not id
      (when (seq (d/query {:query {:find ['?e]
                                   :in '[$ ?account-set ?numeric-code]
                                   :where ['[?e :account/account-set ?account-set]
                                           '[?e :account/numeric-code ?numeric-code]]}
                           :args [(d/db (d/connect uri)) account-set numeric-code]}))

        (throw (ex-info (str "Account set " account-set " already has an account for code " numeric-code)
                        {} ))))

    (let [original (if id (d/entity (d/db (d/connect uri)) id))
          result (audit-transact (cond-> 
                                  [(remove-nils
                                    {:db/id (or id "new-account")
                                     :account/name name
                                     :account/type (keyword "account-type" (clojure.core/name type))
                                     :account/applicability (enum->keyword applicability "account-applicability")
                                     :account/account-set account-set
                                     :account/location location
                                     :account/numeric-code (if-not id
                                                             numeric-code)
                                     :account/code (if-not id
                                                     (str numeric-code))})
                                   [:reset (or id "new-account") :account/client-overrides
                                    (mapv
                                     (fn [client-override]
                                       (remove-nils 
                                        {:db/id (:id client-override)
                                         :account-client-override/client (:client-id client-override)
                                         :account-client-override/name (:name client-override)}))
                                     client-overrides)]]
                                   (and (not location) (:account/location original)) (conj [:db/retract (or id "new-account") :account/location (:account/location original)]))
                                 (:id context))]
      (->graphql 
       (d-accounts/get-by-id (or id (get-in result [:tempids "new-account"])))))))

