Skip to content

brabster/dynamodb-expressions

Repository files navigation

dynamodb-expressions

https://img.shields.io/travis/brabster/dynamodb-expressions.svg https://img.shields.io/github/release/brabster/dynamodb-expressions.svg

DynamoDB Update Expressions in Clojure, designed for use with Amazonica.

Get the latest version on Clojars

Why?

DynamoDB’s native update expression syntax requires placeholders be specified for all values and, under some circumstances, for names too. That typically means (in my experience, anyway) verbose, brittle and hard-to-read code.

The nested-map structure also makes these values hard to manipulate in a threading-friendly way.

Contrived, worst-case example: we want to update a customer document, primary key “customer-id”, adding 1 to the auth-attempts key, and setting the nested call.at key to “today”.

Because auth-attempts includes a hyphen, and both call and at are DynamoDB reserved words, we must set name placeholders for them. We might write something like this:

{:key {:customer-id "foo"}
 :update-expression "ADD #auth_attempts :auth_attempts_val SET #call.#at = :call_at_value"
 :expression-attribute-names {"#auth_attempts" "auth-attempts"
                              "#call" "call"
                              "#at" "at"}
 :expression-attribute-values {":auth_attempts_val" 1
                               ":call_at_value" "today"}}

I don’t think that expresses what I’m trying to do very clearly. This library allows you to write instead:

(require '[dynamodb-expression.core :as dx])

(->
  (dx/update-expr {:customer-id "foo"})
  (dx/add :auth-attempts 1)
  (dx/set [:call :at] "today")
  dx/expr)

Which produces something like the following, applying placeholders for all names. Some indication of where the placeholder came from is retained to help debugging:

{:update-expression
 "ADD #nauth_attempts_21478 :vauth_attempts_21478 SET #ncall_21479.#ncall_at_21480 = :vcall_at_21480"
 :key {:customer-id "foo"}
 :expression-attribute-names {"#nauth_attempts_21478" "auth-attempts"
                              "#ncall_at_21480" "at"
                              "#ncall_21479" "call"},
 :expression-attribute-values {":vauth_attempts_21478" 1
                               ":vcall_at_21480" "today"}}

Unsupported Functionality

The following update expression features are not supported (yet!). Raise an issue and/or submit a PR if you need these.

array syntax

There’s no way to access array elements right now.

functions

Nor can you use functions like list_append.

dynamodb Grammar

To test condition expressions without nasty string hacking, there’s a grammar for condition expressions, based on the documentation.

License

Copyright © 2016 Paul Brabban

Distributed under the Eclipse Public License either version 1.0 or (at your option) any later version.