         (first)
         (keyword))))
 
+(defn- dispatch
+  [opts & args]
+  (:alg opts))
+  ;; (let [alg1 (:algorithm opts)
+  ;;       alg2 (:alg opts)]
+  ;;   (or alg2 alg1)))
+
 (defmulti derive-password
   "Derive key depending on algorithm."
-  :algorithm)
+  dispatch)
 
 (defmulti check-password
   "Password verification implementation."
-  :algorithm)
+  dispatch)
 
 (defmulti format-password
   "Format password depending on algorithm."
-  :algorithm)
+  dispatch)
 
 (defmulti must-update?
   "Check if the current password configuration
   is succeptible to be updatable."
-  :algorithm)
+  dispatch)
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ;; Key Derivation
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 
 (defmethod derive-password :pbkdf2+sha1
-  [{:keys [algorithm password salt iterations] :as pwdparams}]
-  (let [salt (->byte-array (or salt (nonce/random-bytes 12)))
-        iterations (or iterations (get *default-iterations* algorithm))
+  [{:keys [alg password salt iterations] :as pwdparams}]
+  (let [salt (->byte-array (or salt (nonce/random-bytes 12)))
+        iterations (or iterations (get *default-iterations* alg))
         pgen (doto (PKCS5S2ParametersGenerator. (SHA1Digest.))
                (.init password salt iterations))
         password (.getKey (.generateDerivedParameters pgen 160))]
-    {:algorithm algorithm
+    {:alg alg
      :password password
      :salt salt
      :iterations iterations}))
 
 (defmethod derive-password :pbkdf2+sha256
-  [{:keys [algorithm password salt iterations] :as pwdparams}]
-  (let [salt (->byte-array (or salt (nonce/random-bytes 12)))
-        iterations (or iterations (get *default-iterations* algorithm))
+  [{:keys [alg password salt iterations] :as pwdparams}]
+  (let [salt (->byte-array (or salt (nonce/random-bytes 12)))
+        iterations (or iterations (get *default-iterations* alg))
         pgen (doto (PKCS5S2ParametersGenerator. (SHA256Digest.))
                (.init password salt iterations))
         password (.getKey (.generateDerivedParameters pgen 160))]
-    {:algorithm algorithm
+    {:alg alg
      :password password
      :salt salt
      :iterations iterations}))
 
 (defmethod derive-password :pbkdf2+sha3_256
-  [{:keys [algorithm password salt iterations] :as pwdparams}]
-  (let [salt (->byte-array (or salt (nonce/random-bytes 12)))
-        iterations (or iterations (get *default-iterations* algorithm))
+  [{:keys [alg password salt iterations] :as pwdparams}]
+  (let [salt (->byte-array (or salt (nonce/random-bytes 12)))
+        iterations (or iterations (get *default-iterations* alg))
         pgen (doto (PKCS5S2ParametersGenerator. (SHA3Digest. 256))
                (.init password salt iterations))
         password (.getKey (.generateDerivedParameters pgen 256))]
-    {:algorithm algorithm
+    {:alg alg
      :password password
      :salt salt
      :iterations iterations}))
 
 (defmethod derive-password :bcrypt+sha512
-  [{:keys [algorithm password salt iterations] :as pwdparams}]
-  (let [salt (->byte-array (or salt (nonce/random-bytes 12)))
-        iterations (or iterations (get *default-iterations* algorithm))
+  [{:keys [alg password salt iterations] :as pwdparams}]
+  (let [salt (->byte-array (or salt (nonce/random-bytes 12)))
+        iterations (or iterations (get *default-iterations* alg))
         iv (BCrypt/gensalt iterations)
         pwd (-> password
                 (bytes/concat salt)

                     (bytes->hex)
                     (scrypt/encrypt cpucost memcost parallelism)
                     (str->bytes))]
    {:algorithm algorithm
     :cpucost cpucost
     :memcost memcost
     :parallelism parallelism

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

(defmethod must-update? :default
  [{:keys [alg iterations]}]
  (let [desired-iterations (get *default-iterations* alg)]
    (and desired-iterations (> desired-iterations iterations))))

(defmethod must-update? :bcrypt+sha512
  [{:keys [alg iterations]}]
  true)

(defmethod must-update? :scrypt
  [{:keys [alg memcost cpucost]}]
  (let [desired-memcost (get-in *default-iterations* [:scrypt :memcost])
        desired-cpucost (get-in *default-iterations* [:scrypt :cpucost])]
    (and desired-cpucost
