Skip to content

Commit

Permalink
[#73] Housekeeping
Browse files Browse the repository at this point in the history
  • Loading branch information
ptaoussanis committed Jan 23, 2016
1 parent 6fbfcb7 commit 9b3dd33
Show file tree
Hide file tree
Showing 2 changed files with 103 additions and 84 deletions.
142 changes: 81 additions & 61 deletions src/taoensso/faraday.clj
Expand Up @@ -680,37 +680,50 @@
(ExpectedAttributeValue. (clj-val->db-val %))))
expected-map)))

(defn clj->db-expr-values-map [m]
(into {} (for [[k v] m]
[k (clj-val->db-val v)])))
(defn- clj->db-expr-vals-map [m] (encore/map-vals clj-val->db-val m))

(def ^:private deprecation-warning-expected_
(delay
(println "Faraday WARNING: `:expected` option is deprecated in favor of `:cond-expr`")))

(def ^:private deprecation-warning-update-map_
(delay
(println "Faraday WARNING: `update-map` is deprecated in favor of `:cond-expr`")))

(defn put-item-request
[table item & [{:keys [return expected return-cc? condition-expression expression-attr-names expression-attr-values]
:or {return :none}}]]
[table item &
[{:keys [return expected return-cc? cond-expr expr-attr-names expr-attr-vals]
:or {return :none}}]]
(doto-cond [g (PutItemRequest.)]
:always (.setTableName (name table))
:always (.setItem (clj-item->db-item item))
expected (.setExpected (expected-values g))
condition-expression (.setConditionExpression condition-expression)
expression-attr-names (.withExpressionAttributeNames expression-attr-names)
expression-attr-values (.withExpressionAttributeValues
(clj->db-expr-values-map expression-attr-values))
return (.setReturnValues (utils/enum g))
return-cc? (.setReturnConsumedCapacity (utils/enum :total))))
:always (.setTableName (name table))
:always (.setItem (clj-item->db-item item))
expected (.setExpected (expected-values g))
cond-expr (.setConditionExpression cond-expr)
expr-attr-names (.withExpressionAttributeNames expr-attr-names)
expr-attr-vals (.withExpressionAttributeValues
(clj->db-expr-vals-map expr-attr-vals))
return (.setReturnValues (utils/enum g))
return-cc? (.setReturnConsumedCapacity (utils/enum :total))))

(defn put-item
"Adds an item (Clojure map) to a table with options:
:return - e/o #{:none :all-old}.
:condition-expression - \"attribute_exists(attr_name) AND|OR ...\"
:expression-attr-names - {\"#attr_name\" \"name\"}
:expression-attr-values - {\":attr_value\" \"value\"}"
[client-opts table item & [{:keys [return expected return-cc? condition-expression]
:as opts}]]
(assert (not (and expected
condition-expression))
"Only one of :expected or :condition-expression should be provided.")
(when expected
(prn "WARNING - :expected is a legacy option and has been deprecated. Please use :condition-expression instead"))
:return - e/o #{:none :all-old}
:cond-expr - \"attribute_exists(attr_name) AND|OR ...\"
:expr-attr-names - {\"#attr_name\" \"name\"}
:expr-attr-vals - {\":attr_value\" \"value\"}
:expected - DEPRECATED in favor of `:cond-expr`,
{<attr> <#{:exists :not-exists [<comparison-operator> <value>] <value>}> ...}
With comparison-operator e/o #{:eq :le :lt :ge :gt :begins-with :between}."

[client-opts table item &
[{:keys [return expected return-cc? cond-expr]
:as opts}]]

(assert (not (and expected cond-expr))
"Only one of :expected or :cond-expr should be provided")

(when expected @deprecation-warning-expected_)

(as-map
(.putItem (db-client client-opts)
(put-item-request table item opts))))
Expand All @@ -729,47 +742,54 @@
update-map)))

(defn update-item-request
[table prim-kvs update-map & [{:keys [return expected return-cc?
condition-expression
update-expression expression-attr-names expression-attr-values]
:or {return :none}}]]
[table prim-kvs update-map &
[{:keys [return expected return-cc?
cond-expr update-expr expr-attr-names expr-attr-vals]
:or {return :none}}]]

(doto-cond [g (UpdateItemRequest.)]
:always (.setTableName (name table))
:always (.setKey (clj-item->db-item prim-kvs))
update-map (.setAttributeUpdates (attribute-updates update-map))
update-expression (.setUpdateExpression update-expression)
expression-attr-names (.withExpressionAttributeNames expression-attr-names)
expression-attr-values (.withExpressionAttributeValues
(clj->db-expr-values-map expression-attr-values))
expected (.setExpected (expected-values g))
condition-expression (.setConditionExpression condition-expression)
return (.setReturnValues (utils/enum g))
return-cc? (.setReturnConsumedCapacity (utils/enum :total))))
:always (.setTableName (name table))
:always (.setKey (clj-item->db-item prim-kvs))
update-map (.setAttributeUpdates (attribute-updates update-map))
update-expr (.setUpdateExpression update-expr)
expr-attr-names (.withExpressionAttributeNames expr-attr-names)
expr-attr-vals (.withExpressionAttributeValues
(clj->db-expr-vals-map expr-attr-vals))
expected (.setExpected (expected-values g))
cond-expr (.setConditionExpression cond-expr)
return (.setReturnValues (utils/enum g))
return-cc? (.setReturnConsumedCapacity (utils/enum :total))))

(defn update-item
"Updates an item in a table by its primary key with options:
prim-kvs - {<hash-key> <val>} or {<hash-key> <val> <range-key> <val>}.
:condition-expression - \"attribute_exists(attr_name) AND|OR ...\"
:update-expression - \"SET #attr_name = :attr_value\"
:expression-attr-names - {\"#attr_name\" \"name\"}
:expression-attr-values - {\":attr_value\" \"value\"}
:return - e/o #{:none :all-old :updated-old :all-new :updated-new}."
([client-opts table prim-kvs update-map & [{:keys [return expected return-cc?
condition-expression update-expression]
:as opts}]]
(assert (not (and expected
condition-expression))
"Only one of :expected or :condition-expression should be provided.")
(assert (not (and (not (empty? update-map))
update-expression))
"Only one of 'update-map' or :update-expression should be provided.")
(when expected
(prn "WARNING - :expected is a legacy option and has been deprecated. Please use :condition-expression instead"))
(when update-map
(prn "WARNING - update-map is a legacy option and has been deprecated. Please use :condition-expression instead"))
prim-kvs - {<hash-key> <val>} or {<hash-key> <val> <range-key> <val>}
update-map - DEPRECATED in favor of `:update-expr`,
{<attr> [<#{:put :add :delete}> <optional value>]}
:cond-expr - \"attribute_exists(attr_name) AND|OR ...\"
:update-expr - \"SET #attr_name = :attr_value\"
:expr-attr-names - {\"#attr_name\" \"name\"}
:expr-attr-vals - {\":attr_value\" \"value\"}
:return - e/o #{:none :all-old :updated-old :all-new :updated-new}
:expected - DEPRECATED in favor of `:cond-expr`,
{<attr> <#{:exists :not-exists [<comparison-operator> <value>] <value>}> ...}
With comparison-operator e/o #{:eq :le :lt :ge :gt :begins-with :between}."

([client-opts table prim-kvs update-map &
[{:keys [return expected return-cc? cond-expr update-expr]
:as opts}]]

(assert (not (and expected cond-expr))
"Only one of :expected or :cond-expr should be provided")

(assert (not (and update-expr (seq update-map)))
"Only one of 'update-map' or :update-expr should be provided")

(when expected @deprecation-warning-expected_)
(when (seq update-map) @deprecation-warning-update-map_)

(as-map
(.updateItem (db-client client-opts)
(update-item-request table prim-kvs update-map opts)))))
(.updateItem (db-client client-opts)
(update-item-request table prim-kvs update-map opts)))))

(defn delete-item-request "Implementation detail."
[table prim-kvs & [{:keys [return expected return-cc?]
Expand Down
45 changes: 22 additions & 23 deletions test/taoensso/faraday/tests/main.clj
Expand Up @@ -95,14 +95,13 @@
*client-opts* ttable {:id 10} {:name [:put "baz"]} {:return :all-new})))

(expect
#= (far/ex :conditional-check-failed)
#=(far/ex :conditional-check-failed)
(far/update-item *client-opts* ttable
{:id 10} {:name [:put "baz"]}
{:expected {:name "garbage"}})))

{:id 10} {:name [:put "baz"]}
{:expected {:name "garbage"}})))

;;;; Expressions support

;; Expressions support
(let [i {:id 10 :name "update me"}]
(after-setup!
#(far/delete-item *client-opts* ttable {:id 10}))
Expand All @@ -111,32 +110,32 @@
{:id 10 :name "foo"}
(do
(far/update-item *client-opts* ttable
{:id 10}
{}
{:update-expression "SET #name = :name"
:expression-attr-names {"#name" "name"}
:expression-attr-values {":name" "foo"}
:return :all-new})))
{:id 10}
{}
{:update-expr "SET #name = :name"
:expr-attr-names {"#name" "name"}
:expr-attr-vals {":name" "foo"}
:return :all-new})))

(expect ; Condition expression support in update-item
#= (far/ex :conditional-check-failed)
#=(far/ex :conditional-check-failed)
(do
(far/update-item *client-opts* ttable
{:id 10}
{}
{:update-expression "SET #name = :name"
:expression-attr-names {"#name" "name"}
:expression-attr-values {":name" "foo"}
:condition-expression "#name <> :name"
:return :all-new})))
{:id 10}
{}
{:cond-expr "#name <> :name"
:update-expr "SET #name = :name"
:expr-attr-names {"#name" "name"}
:expr-attr-vals {":name" "foo"}
:return :all-new})))

(expect ; Condition expression support in put-item
#= (far/ex :conditional-check-failed)
#=(far/ex :conditional-check-failed)
(do
(far/put-item *client-opts* ttable i
{:condition-expression "attribute_not_exists(id) AND #name <> :name"
:expression-attr-names {"#name" "name"}
:expression-attr-values {":name" "foo"}}))))
{:cond-expr "attribute_not_exists(id) AND #name <> :name"
:expr-attr-names {"#name" "name"}
:expr-attr-vals {":name" "foo"}}))))

(let [items [{:id 11 :name "eleven" :test "batch"}
{:id 12 :name "twelve" :test "batch"}
Expand Down

0 comments on commit 9b3dd33

Please sign in to comment.