payroll-import/src/core.clj

87 lines
4 KiB
Clojure
Raw Normal View History

2024-02-21 23:11:07 +00:00
;; Copyright 2024 Ben Sturmfels
;; License: GPLv3-or-later
(ns core
2024-02-21 23:11:07 +00:00
"Beancount importer for Paychex Pay Item Details report."
(:require [clojure.tools.cli :refer [parse-opts]]
2024-02-21 23:11:07 +00:00
[import :as import])
(:gen-class))
(def cli-options
[[nil "--csv FILE" "Pay Item Details CSV report"]
2024-02-21 23:11:07 +00:00
[nil "--date DATE" "Date used for the transactions (YYYY-MM-DD)"
:validate [#(re-matches #"\d{4}-\d{2}-\d{2}" %) "Must be of format YYYY-MM-DD"]
2024-02-21 23:11:07 +00:00
:default "TODO-DATE"]
[nil "--period PERIOD" "Month/year covered by the pay run eg. \"December 2023\""
2024-02-21 23:11:07 +00:00
:default "TODO-PERIOD"]
[nil "--total-fees NUM" "Total fee charged by Paychex, eg. \"206.50\""
:parse-fn bigdec
:default 0M]
2024-02-21 23:11:07 +00:00
[nil "--pay-receipt-no REFERENCE" "Payroll receipt number, eg. \"rt:111/222\""
:default "TODO-PAY-RECEIPT"]
[nil "--fees-receipt-no REFERENCE" "Paychex fees receipt number, eg. \"rt:111/222\""
2024-02-21 23:11:07 +00:00
:default "TODO-FEES-RECEIPT"]
[nil "--fees-invoice-no REFERENCE" "Paychex fees invoice number, eg. \"rt:111/222\""
2024-02-21 23:11:07 +00:00
:default "TODO-FEES-INVOICE"]
[nil "--retirement-receipt-no REFERENCE" "Retirement receipt number, eg. \"rt:111/222\""
2024-02-21 23:11:07 +00:00
:default "TODO-RETIREMENT-RECEIPT"]
[nil "--retirement-invoice-no REFERENCE" "Retirement receipt number, eg. \"rt:111/222\""
2024-02-21 23:11:07 +00:00
:default "TODO-RETIREMENT-INVOICE"]
["-h" "--help"]])
(defn -main [& args]
(let [{:keys [options _arguments _errors summary]} (parse-opts args cli-options)
{:keys [date period pay-receipt-no total-fees fees-receipt-no fees-invoice-no retirement-receipt-no retirement-invoice-no]} options]
(when (:help options)
(println summary)
(System/exit 0))
(let [data (import/read-csv (:csv options))
imported (concat (import/payroll date period pay-receipt-no data)
(import/individual-taxes date period pay-receipt-no retirement-invoice-no data)
(import/employer-taxes date period pay-receipt-no data)
(import/payroll-fees date period fees-receipt-no fees-invoice-no total-fees data)
(import/retirement date period retirement-receipt-no retirement-invoice-no data))]
(doseq [i imported]
(println (import/render-transaction i))))))
(comment
2024-02-21 23:11:07 +00:00
;; Examples to exercise the importer during development.
(require
'[parse :refer [parse sort-postings]]
'[lambdaisland.deep-diff2 :as dd])
;; These examples are not included with the code for privacy reasons.
(require '[examples])
(def data (import/read-csv "/home/ben/Downloads/2023-12-27_Pay-Item-Details_2023-12-2.csv"))
(def imported
(concat (import/payroll "2023-12-29" "December 2023" "rt:19462/674660" data)
(import/individual-taxes "2023-12-29" "December 2023" "rt:19462/674660" "rt:19403/675431" data)
(import/employer-taxes "2023-12-29" "December 2023" "rt:19462/674660" data)
(import/payroll-fees "2023-12-29" "December 2023" "rt:19459/675387" "rt:19459/674887" 206.50M data)
(import/retirement "2024-01-02" "December 2023" "rt:19403/676724" "rt:19403/675431" data)))
2024-02-20 03:55:14 +00:00
(dd/pretty-print
(dd/diff
2024-02-21 23:11:07 +00:00
(sort-postings (parse examples/dec-2023))
2024-02-20 03:55:14 +00:00
(sort-postings imported)))
(def data (import/read-csv "/home/ben/Downloads/2024-01-29_Pay-Item-Details_2024-01.csv"))
(def imported
(concat (import/payroll "2024-01-31" "January 2024" "rt:19462/685751" data)
(import/individual-taxes "2024-01-31" "January 2024" "rt:19462/685751" "rt:19403/685602" data)
(import/employer-taxes "2024-01-31" "January 2024" "rt:19462/685751" data)
(import/payroll-fees "2024-01-31" "January 2024" "rt:19459/675387" "rt:19459/674887" 206.50M data)
(import/retirement "2024-01-31" "January 2024" "rt:19403/685929" "rt:19403/685602" data)))
2024-02-21 23:11:07 +00:00
;; Compare hand-written transactions with imported (ignoring ordering).
(dd/pretty-print
(dd/diff
2024-02-21 23:11:07 +00:00
(sort-postings (parse examples/jan-2024))
(sort-postings imported)))
2024-02-21 23:11:07 +00:00
;; Print out text transactions
(doseq [i imported]
(println (import/render-transaction i)))
)