Compare commits
5 commits
main
...
credential
Author | SHA1 | Date | |
---|---|---|---|
4330173084 | |||
5c583fd72f | |||
21dee3cfc0 | |||
b96f51220d | |||
a4ff484ef8 |
4 changed files with 129 additions and 1 deletions
4
deps.edn
4
deps.edn
|
@ -11,7 +11,9 @@
|
|||
{;; Application
|
||||
org.clojure/clojure {:mvn/version "1.11.4"}
|
||||
org.clojure/spec.alpha {:mvn/version "0.5.238"}
|
||||
orchestra/orchestra {:mvn/version "2021.01.01-1"}}
|
||||
orchestra/orchestra {:mvn/version "2021.01.01-1"}
|
||||
cheshire/cheshire {:mvn/version "5.13.0"}
|
||||
com.widdindustries/cljc.java-time {:mvn/version "0.1.21"}}
|
||||
;; ---------------------------------------------------------
|
||||
|
||||
;; ---------------------------------------------------------
|
||||
|
|
22
src/dda/backup/cred_rot.clj
Normal file
22
src/dda/backup/cred_rot.clj
Normal file
|
@ -0,0 +1,22 @@
|
|||
(ns dda.backup.cred-rot
|
||||
(:require
|
||||
[orchestra.core :refer [defn-spec]]
|
||||
[clojure.spec.alpha :as s]
|
||||
[dda.backup.cred-rot.domain :as domain]))
|
||||
|
||||
(s/def ::new-password-file string?)
|
||||
|
||||
(s/def ::cred-rot
|
||||
(s/keys :req-un []
|
||||
:opt-un [::new-password-file]))
|
||||
|
||||
; Refer to "docs/CredentialRotation.md" for specifics
|
||||
|
||||
(defn-spec maybe-add-new! nil?
|
||||
[config ::cred-rot]
|
||||
(when-let [{:keys [new-password-file]} config]
|
||||
(domain/add-new-password! new-password-file)))
|
||||
|
||||
(defn-spec replace-old-password! nil?
|
||||
[]
|
||||
)
|
71
src/dda/backup/cred_rot/domain.clj
Normal file
71
src/dda/backup/cred_rot/domain.clj
Normal file
|
@ -0,0 +1,71 @@
|
|||
(ns dda.backup.cred-rot.domain
|
||||
(:require
|
||||
[orchestra.core :refer [defn-spec]]
|
||||
[clojure.spec.alpha :as s]
|
||||
[clojure.string :as str]
|
||||
[dda.backup.core.domain :as cd]
|
||||
[dda.backup.restic.domain :as rd]
|
||||
[cljc.java-time.local-date :as ld]
|
||||
[cljc.java-time.format.date-time-formatter :as df]))
|
||||
|
||||
(s/def ::new-password-file string?)
|
||||
(s/def ::config (s/keys :req-un [::rd/restic-repository
|
||||
::rd/password-file]
|
||||
:opt-un [::rd/certificate-file
|
||||
::new-password-file]))
|
||||
|
||||
(def lowercase-numeric #"[a-z0-9]+")
|
||||
(def alphanumeric #"[a-zA-Z0-9]+")
|
||||
; true | false
|
||||
(s/def ::current boolean?)
|
||||
; 521e0760
|
||||
(s/def ::id (s/and string? #(re-matches lowercase-numeric %)))
|
||||
; root
|
||||
(s/def ::userName #(re-matches alphanumeric %))
|
||||
; backup-restore-65bd9b6ff5-z69sn
|
||||
(s/def ::hostName (fn [in] (every? #(re-matches lowercase-numeric %) (str/split in #"-"))))
|
||||
; "2024-10-18 13:08:16"
|
||||
(def timestamp-formatter (df/of-pattern "yyyy-MM-dd HH:mm:ss"))
|
||||
(s/def ::created #(try
|
||||
(ld/parse % timestamp-formatter)
|
||||
true
|
||||
(catch Exception _ false)))
|
||||
|
||||
(s/def ::entry (s/keys :opt-un []
|
||||
:req-un [::current ::id ::userName ::hostName ::created]))
|
||||
(s/def ::response (s/coll-of ::entry))
|
||||
|
||||
|
||||
; Refer to "docs/CredentialRotation.md" for specifics
|
||||
|
||||
(defn-spec base-command ::cd/command
|
||||
[config ::config
|
||||
command ::cd/command]
|
||||
(let [{:keys [restic-repository password-file
|
||||
certificate-file new-password-file]} config]
|
||||
(into
|
||||
[]
|
||||
(concat ["restic" "-r" restic-repository]
|
||||
(cond
|
||||
(some? certificate-file)
|
||||
["--cacert" certificate-file]
|
||||
(some? password-file)
|
||||
["--password-file" password-file]
|
||||
:else
|
||||
[])
|
||||
command))))
|
||||
|
||||
(defn-spec list-passwords-command ::cd/command
|
||||
[config ::config]
|
||||
(base-command config ["key" "list" "--json"]))
|
||||
|
||||
(defn-spec add-password-command ::cd/command
|
||||
[config ::config]
|
||||
(let [{:keys [new-password-file]} config]
|
||||
(base-command config ["key" "add" "--new-password-file" new-password-file])))
|
||||
|
||||
(defn-spec remove-password-command ::cd/command
|
||||
[config ::config
|
||||
new-id ::id
|
||||
old-id ::id]
|
||||
(base-command config ["key" "remove" "--key-hint" new-id old-id]))
|
33
test/dda/backup/cred_rot/domain_test.clj
Normal file
33
test/dda/backup/cred_rot/domain_test.clj
Normal file
|
@ -0,0 +1,33 @@
|
|||
(ns dda.backup.cred-rot.domain-test
|
||||
(:require
|
||||
[clojure.test :refer [deftest is]]
|
||||
[clojure.spec.alpha :as s]
|
||||
[clojure.spec.test.alpha :as st]
|
||||
[dda.backup.cred-rot.domain :as cut]))
|
||||
|
||||
(deftest test-spec-id
|
||||
(is (s/valid? ::cut/id "521e0760"))
|
||||
(is (s/valid? ::cut/id "test"))
|
||||
(is (s/valid? ::cut/id "123456"))
|
||||
(is (not (s/valid? ::cut/id "ROOT")))
|
||||
(is (not (s/valid? ::cut/id "Test!"))))
|
||||
|
||||
(deftest test-spec-username
|
||||
(is (s/valid? ::cut/userName "521e0760"))
|
||||
(is (s/valid? ::cut/userName "Testuser"))
|
||||
(is (s/valid? ::cut/userName "root"))
|
||||
(is (s/valid? ::cut/userName "ROOT"))
|
||||
(is (not (s/valid? ::cut/userName "test-user"))))
|
||||
|
||||
(deftest test-spec-hostName
|
||||
(let [valid #(s/valid? ::cut/hostName %)]
|
||||
(is (valid "test-some-combination-2"))
|
||||
(is (valid "backup-restore-65bd9b6ff5-z69sn"))))
|
||||
|
||||
(deftest test-spec-created
|
||||
(let [valid #(s/valid? ::cut/created %)]
|
||||
(is (valid "2024-10-18 13:08:16"))
|
||||
(is (valid "2032-09-01 12:56:59"))
|
||||
(is (not (valid "2024-13-5 13:08:16")))
|
||||
(is (not (valid "2024-6-42 13:08:16")))
|
||||
(is (not (valid "test")))))
|
Loading…
Reference in a new issue