diff --git a/src/alas.janet b/src/alas.janet index db33079..6ded593 100644 --- a/src/alas.janet +++ b/src/alas.janet @@ -5,13 +5,11 @@ (import ./commands :prefix "") +(import ./errors) (import ./file_repository) (import ./plan/parser :as plan_parser) (import ./plan/serializer :as plan_serializer) -(defn- print-errors [errors] - (each error errors (print (string error ".")))) - # Keep commands sorted alphabetically. (def argparse-params ["A command line utility for planning your days" @@ -42,19 +40,21 @@ (def load-file-result (file_repository/load file-path)) (def errors (load-file-result :errors)) (if errors - (print-errors errors) + (errors/print-errors errors (errors/exit-status-codes :file-error)) (let [plan-string (load-file-result :text) parse-result (plan_parser/parse plan-string) parse-errors (parse-result :errors) plan (parse-result :plan)] (if parse-errors - (print-errors parse-errors) - (let [serialize-empty-inbox (plan_parser/serialize-empty-inbox? plan-string) - new-plan (run-commands plan file-path arguments) - new-plan-string (plan_serializer/serialize + (errors/print-errors parse-errors (errors/exit-status-codes :parse-error)) + (let [{:plan new-plan :errors run-errors} (run-commands plan file-path arguments)] + (if (empty? run-errors) + (let [serialize-empty-inbox (plan_parser/serialize-empty-inbox? plan-string) + new-plan-string (plan_serializer/serialize new-plan {:serialize-empty-inbox serialize-empty-inbox})] - (file_repository/save new-plan-string file-path)))))) + (file_repository/save new-plan-string file-path)) + (errors/print-errors run-errors (errors/exit-status-codes :command-error)))))))) (defn- run-with-arguments [arguments] (def file-path (arguments :default)) @@ -62,7 +62,8 @@ (run-with-file-path arguments file-path) (if (arguments "version") (print-version) - (print "Plan file path missing.")))) + (errors/print-errors ["Plan file path is missing"] + (errors/exit-status-codes :plan-path-missing))))) ## ————————————————————————————————————————————————————————————————————————————————————————————————— ## Public Interface diff --git a/src/commands.janet b/src/commands.janet index dbafa10..69c9ecc 100644 --- a/src/commands.janet +++ b/src/commands.janet @@ -12,6 +12,7 @@ (import ./commands/stats) (import ./date :as d) +(import ./errors) (import ./schedule_parser) # backup command needs to be first @@ -27,10 +28,6 @@ schedule_tasks/build-command stats/build-command]) -(defn- print-errors [errors] - (loop [error :in errors] - (print error))) - ## ————————————————————————————————————————————————————————————————————————————————————————————————— ## Public Interface @@ -49,13 +46,12 @@ (defn run-commands [plan file-path arguments] (def commands (build-commands arguments file-path)) (def errors (filter identity (flatten (map (fn [c] (c :errors)) commands)))) - (if (any? errors) - (do - (print-errors errors) - plan) - (reduce (fn [new-plan command-and-arguments] - (def command (first (command-and-arguments :command))) - (def arguments (drop 1 (command-and-arguments :command))) - (apply command new-plan arguments)) - plan - commands))) + (var new-plan plan) + (if (empty? errors) + (set new-plan (reduce (fn [new-plan command-and-arguments] + (def command (first (command-and-arguments :command))) + (def arguments (drop 1 (command-and-arguments :command))) + (apply command new-plan arguments)) + plan + commands))) + {:plan new-plan :errors errors}) diff --git a/src/commands/list_contacts.janet b/src/commands/list_contacts.janet index 121ede2..eb7a51a 100644 --- a/src/commands/list_contacts.janet +++ b/src/commands/list_contacts.janet @@ -3,6 +3,7 @@ (import ../utils :prefix "") (import ../date :as d) +(import ../errors) (import ../contact/repository :as contacts_repository) (defn- to-csv-line [contact] @@ -35,6 +36,6 @@ (let [load-result (contacts_repository/load-contacts argument) errors (load-result :errors)] (if errors - {:errors (format-command-errors "--list-contacts" errors)} + {:errors (errors/format-command-errors "--list-contacts" errors)} {:command [print-contacts (load-result :contacts)]})) {})) diff --git a/src/commands/schedule_contacts.janet b/src/commands/schedule_contacts.janet index 6ef4b73..9f3f1eb 100644 --- a/src/commands/schedule_contacts.janet +++ b/src/commands/schedule_contacts.janet @@ -1,6 +1,7 @@ ### ———————————————————————————————————————————————————————————————————————————————————————————————— ### This module implements a command for scheduling contacts for today in a plan. +(import ../errors) (import ../utils :prefix "") (import ../contact) @@ -69,6 +70,6 @@ errors (load-result :errors) contacts (load-result :contacts)] (if errors - {:errors (format-command-errors "--schedule-contacts" errors)} + {:errors (errors/format-command-errors "--schedule-contacts" errors)} {:command [schedule-contacts contacts (date/today)]})) {})) diff --git a/src/commands/schedule_tasks.janet b/src/commands/schedule_tasks.janet index e384fc2..0f63c20 100644 --- a/src/commands/schedule_tasks.janet +++ b/src/commands/schedule_tasks.janet @@ -8,6 +8,7 @@ (import ../plan) (import ../task) +(import ../errors) (import ../file_repository) (import ../schedule_parser) @@ -84,10 +85,10 @@ (let [load-file-result (file_repository/load argument) errors (load-file-result :errors)] (if errors - {:errors (format-command-errors command errors)} + {:errors (errors/format-command-errors command errors)} (let [parse-result (schedule_parser/parse (load-file-result :text)) errors (parse-result :errors)] (if errors - {:errors (format-command-errors command errors)} + {:errors (errors/format-command-errors command errors)} {:command [schedule-tasks (parse-result :tasks) (date/today)]})))) {})) diff --git a/src/errors.janet b/src/errors.janet new file mode 100644 index 0000000..781249d --- /dev/null +++ b/src/errors.janet @@ -0,0 +1,19 @@ +### ———————————————————————————————————————————————————————————————————————————————————————————————— +### Errors. + +## ————————————————————————————————————————————————————————————————————————————————————————————————— +## Public Interface + +(def exit-status-codes + {:error 1 + :plan-path-missing 2 + :file-error 3 + :parse-error 4 + :command-error 5}) + +(defn format-command-errors [command errors] + (map (fn [error] (string command " " (string/ascii-lower error))) errors)) + +(defn print-errors [errors exit-status-code] + (each error errors (print (string error "."))) + (os/exit exit-status-code)) diff --git a/src/utils.janet b/src/utils.janet index 873a099..b4b5ff1 100644 --- a/src/utils.janet +++ b/src/utils.janet @@ -13,6 +13,3 @@ (if (string/has-suffix? "/" path) (string/trimr path "/") path)) - -(defn format-command-errors [command errors] - (map (fn [error] (string command " " (string/ascii-lower error) ".")) errors)) diff --git a/test/commands/list_contacts_test.janet b/test/commands/list_contacts_test.janet index 27deb40..ee531c9 100644 --- a/test/commands/list_contacts_test.janet +++ b/test/commands/list_contacts_test.janet @@ -32,4 +32,4 @@ (deftest "when the directory doesn't exist" (def arguments {"list-contacts" "test/missing-directory"}) (def result (build-command arguments)) - (test (first (result :errors)) "--list-contacts directory does not exist.")) + (test (first (result :errors)) "--list-contacts directory does not exist")) diff --git a/test/commands/schedule_contacts_test.janet b/test/commands/schedule_contacts_test.janet index 5516b8d..d4008c4 100644 --- a/test/commands/schedule_contacts_test.janet +++ b/test/commands/schedule_contacts_test.janet @@ -127,4 +127,4 @@ (def arguments {"schedule-contacts" "test/examples/people"}) (def result (build-command arguments)) (test (nil? (result :command)) true) - (test (first (result :errors)) "--schedule-contacts directory does not exist.")) + (test (first (result :errors)) "--schedule-contacts directory does not exist")) diff --git a/test/commands/schedule_tasks_test.janet b/test/commands/schedule_tasks_test.janet index b637e7f..f7bf229 100644 --- a/test/commands/schedule_tasks_test.janet +++ b/test/commands/schedule_tasks_test.janet @@ -225,16 +225,16 @@ (def arguments {"schedule-tasks" "test/examples/missing-schedule.md"}) (def result (build-command arguments)) (test (nil? (result :command)) true) - (test (first (result :errors)) "--schedule-tasks file does not exist.")) + (test (first (result :errors)) "--schedule-tasks file does not exist")) (deftest "returns an error when the schedule cannot be parsed" (def arguments {"schedule-tasks" "test/examples/unparsable-schedule.md"}) (def result (build-command arguments)) (test (nil? (result :command)) true) - (test (first (result :errors)) "--schedule-tasks schedule can not be parsed.")) + (test (first (result :errors)) "--schedule-tasks schedule can not be parsed")) (deftest "returns an error when the schedule is empty" (def arguments {"schedule-tasks" "test/examples/empty-schedule.md"}) (def result (build-command arguments)) (test (nil? (result :command)) true) - (test (first (result :errors)) "--schedule-tasks schedule is empty.")) + (test (first (result :errors)) "--schedule-tasks schedule is empty")) diff --git a/test/commands_test.janet b/test/commands_test.janet index 72ee8ad..83a06ca 100644 --- a/test/commands_test.janet +++ b/test/commands_test.janet @@ -54,8 +54,9 @@ (day/build-day (d/date 2020 8 2) @[] @[(task/build-task "Buy milk" true)])])) (def arguments {"skip-backup" true "remove-empty-days" true "insert-days" "3"}) - (def new-plan (run-commands plan file-path arguments)) + (def {:plan new-plan :errors errors} (run-commands plan file-path arguments)) (def days (new-plan :days)) + (test (empty? errors) true) (test (length days) 4) (test (= (d/+days today 2) ((days 0) :date)) true) (test (= (d/+days today 1) ((days 1) :date)) true) @@ -70,9 +71,10 @@ (day/build-day (d/date 2020 8 2) @[] @[(task/build-task "Buy milk" true)])])) (def arguments {"skip-backup" true "remove-empty-days" true "insert-days" "three"}) - (def new-plan (run-commands plan file-path arguments)) + (def {:plan new-plan :errors errors} (run-commands plan file-path arguments)) (def days (new-plan :days)) (test (length days) 3) (test (= today ((days 0) :date)) true) (test (= (d/date 2020 8 4) ((days 1) :date)) true) - (test (= (d/date 2020 8 2) ((days 2) :date)) true)) + (test (= (d/date 2020 8 2) ((days 2) :date)) true) + (test (= (first errors) "--insert-days argument is not a number.") true)) diff --git a/test/examples/my-plan.md b/test/examples/my-plan.md deleted file mode 100644 index f22af81..0000000 --- a/test/examples/my-plan.md +++ /dev/null @@ -1,3 +0,0 @@ -# My Plan - -## 2022-05-12 diff --git a/test/examples/todo-2022-02-10.md b/test/examples/todo-2022-02-10.md deleted file mode 100644 index 713d15e..0000000 --- a/test/examples/todo-2022-02-10.md +++ /dev/null @@ -1,13 +0,0 @@ -# Main TODO - -## Inbox - -## 2020-08-01, Saturday - -- [ ] Develop photos for the grandmother -- [X] Pay bills - -## 2020-07-31, Friday - -- [X] Review open pull requests -- [X] Fix flaky test